1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
|
/********************* */
/*! \file trigger_term_info.h
** \verbatim
** Top contributors (to current version):
** Andrew Reynolds, Morgan Deters
** This file is part of the CVC4 project.
** Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
** in the top-level source directory and their institutional affiliations.
** All rights reserved. See the file COPYING in the top-level source
** directory for licensing information.\endverbatim
**
** \brief trigger term info class
**/
#include "cvc4_private.h"
#ifndef CVC4__THEORY__QUANTIFIERS__TRIGGER_TERM_INFO_H
#define CVC4__THEORY__QUANTIFIERS__TRIGGER_TERM_INFO_H
#include <map>
#include "expr/node.h"
namespace cvc5 {
namespace theory {
namespace quantifiers {
namespace inst {
/** Information about a node used in a trigger.
*
* This information includes:
* 1. the free variables of the node, and
* 2. information about which terms are useful for matching.
*
* As an example, consider the trigger
* { f( x ), g( y ), P( y, z ) }
* for quantified formula
* forall xy. ( f( x ) != b => ( P( x, g( y ) ) V P( y, z ) ) )
*
* Notice that it is only useful to match f( x ) to f-applications not in the
* equivalence class of b, and P( y, z ) to P-applications not in the
* equivalence class of true, as such instances will always be entailed by the
* ground equalities and disequalities the current context. Entailed instances
* are typically not helpful, and are discarded in
* Instantiate::addInstantiation(...) unless the option --no-inst-no-entail is
* enabled. For more details, see page 10 of "Congruence Closure with Free
* Variables", Barbosa et al., TACAS 2017.
*
* This example is referenced for each of the functions below.
*/
class TriggerTermInfo
{
public:
TriggerTermInfo() : d_reqPol(0), d_weight(0) {}
~TriggerTermInfo() {}
/** The free variables in the node
*
* In the trigger term info for f( x ) in the above example, d_fv = { x }
* In the trigger term info for g( y ) in the above example, d_fv = { y }
* In the trigger term info for P( y, z ) in the above example, d_fv = { y, z
* }
*/
std::vector<Node> d_fv;
/** Required polarity: 1 for equality, -1 for disequality, 0 for none
*
* In the trigger term info for f( x ) in the above example, d_reqPol = -1
* In the trigger term info for g( y ) in the above example, d_reqPol = 0
* In the trigger term info for P( y, z ) in the above example, d_reqPol = 1
*/
int d_reqPol;
/** Required polarity equal term
*
* If d_reqPolEq is not null,
* if d_reqPol = 1, then this trigger term must be matched to terms in the
* equivalence class of d_reqPolEq,
* if d_reqPol = -1, then this trigger term must be matched to terms *not*
* in the equivalence class of d_reqPolEq.
*
* This information is typically chosen by analyzing the entailed equalities
* and disequalities of quantified formulas.
* In the trigger term info for f( x ) in the above example, d_reqPolEq = b
* In the trigger term info for g( y ) in the above example,
* d_reqPolEq = Node::null()
* In the trigger term info for P( y, z ) in the above example,
* d_reqPolEq = false
*/
Node d_reqPolEq;
/** the weight of the trigger (see getTriggerWeight). */
int32_t d_weight;
/** Initialize this information class (can be called more than once).
* q is the quantified formula that n is a trigger term for
* n is the trigger term
* reqPol/reqPolEq are described above
*/
void init(Node q, Node n, int reqPol = 0, Node reqPolEq = Node::null());
/** is n an atomic trigger?
*
* An atomic trigger is one whose kind is an atomic trigger kind.
*/
static bool isAtomicTrigger(Node n);
/** Is k an atomic trigger kind?
*
* An atomic trigger kind is one for which term indexing/matching is possible.
*/
static bool isAtomicTriggerKind(Kind k);
/** is n a relational trigger, e.g. like x >= a ? */
static bool isRelationalTrigger(Node n);
/** Is k a relational trigger kind? */
static bool isRelationalTriggerKind(Kind k);
/** is n a simple trigger (see inst_match_generator.h)? */
static bool isSimpleTrigger(Node n);
/** get trigger weight
*
* Intutively, this function classifies how difficult it is to handle the
* trigger term n, where the smaller the value, the easier.
*
* Returns 0 for triggers that are APPLY_UF terms.
* Returns 1 for other triggers whose kind is atomic.
* Returns 2 otherwise.
*/
static int32_t getTriggerWeight(Node n);
};
} // namespace inst
} // namespace quantifiers
} // namespace theory
} // namespace cvc5
#endif
|