GCC Code Coverage Report
Directory: . Exec Total Coverage
File: src/theory/bags/bags_rewriter.h Lines: 2 2 100.0 %
Date: 2021-08-14 Branches: 0 0 0.0 %

Line Exec Source
1
/******************************************************************************
2
 * Top contributors (to current version):
3
 *   Mudathir Mohamed, Gereon Kremer
4
 *
5
 * This file is part of the cvc5 project.
6
 *
7
 * Copyright (c) 2009-2021 by the authors listed in the file AUTHORS
8
 * in the top-level source directory and their institutional affiliations.
9
 * All rights reserved.  See the file COPYING in the top-level source
10
 * directory for licensing information.
11
 * ****************************************************************************
12
 *
13
 * Bags theory rewriter.
14
 */
15
16
#include "cvc5_private.h"
17
18
#ifndef CVC5__THEORY__BAGS__THEORY_BAGS_REWRITER_H
19
#define CVC5__THEORY__BAGS__THEORY_BAGS_REWRITER_H
20
21
#include "theory/bags/rewrites.h"
22
#include "theory/theory_rewriter.h"
23
#include "util/statistics_stats.h"
24
25
namespace cvc5 {
26
namespace theory {
27
namespace bags {
28
29
/** a class represents the result of rewriting bag nodes */
30
9363
struct BagsRewriteResponse
31
{
32
  BagsRewriteResponse();
33
  BagsRewriteResponse(Node n, Rewrite rewrite);
34
  BagsRewriteResponse(const BagsRewriteResponse& r);
35
  /** the rewritten node */
36
  Node d_node;
37
  /** type of rewrite used by bags */
38
  Rewrite d_rewrite;
39
40
}; /* struct BagsRewriteResponse */
41
42
9977
class BagsRewriter : public TheoryRewriter
43
{
44
 public:
45
  BagsRewriter(HistogramStat<Rewrite>* statistics = nullptr);
46
47
  /**
48
   * postRewrite nodes with kinds: MK_BAG, BAG_COUNT, UNION_MAX, UNION_DISJOINT,
49
   * INTERSECTION_MIN, DIFFERENCE_SUBTRACT, DIFFERENCE_REMOVE, BAG_CHOOSE,
50
   * BAG_CARD, BAG_IS_SINGLETON.
51
   * See the rewrite rules for these kinds below.
52
   */
53
  RewriteResponse postRewrite(TNode n) override;
54
  /**
55
   * preRewrite nodes with kinds: EQUAL, SUBBAG.
56
   * See the rewrite rules for these kinds below.
57
   */
58
  RewriteResponse preRewrite(TNode n) override;
59
 private:
60
  /**
61
   * rewrites for n include:
62
   * - (= A A) = true where A is a bag
63
   */
64
  BagsRewriteResponse preRewriteEqual(const TNode& n) const;
65
66
  /**
67
   * rewrites for n include:
68
   * - (bag.is_included A B) = ((difference_subtract A B) == emptybag)
69
   */
70
  BagsRewriteResponse rewriteSubBag(const TNode& n) const;
71
72
  /**
73
   * rewrites for n include:
74
   * - (bag x 0) = (emptybag T) where T is the type of x
75
   * - (bag x (-c)) = (emptybag T) where T is the type of x, and c > 0 is a
76
   *   constant
77
   * - otherwise = n
78
   */
79
  BagsRewriteResponse rewriteMakeBag(const TNode& n) const;
80
81
  /**
82
   * rewrites for n include:
83
   * - (bag.count x emptybag) = 0
84
   * - (bag.count x (bag x c) = c
85
   * - otherwise = n
86
   */
87
  BagsRewriteResponse rewriteBagCount(const TNode& n) const;
88
89
  /**
90
   *  rewrites for n include:
91
   *  - (duplicate_removal (bag x n)) = (bag x 1)
92
   *     where n is a positive constant
93
   */
94
  BagsRewriteResponse rewriteDuplicateRemoval(const TNode& n) const;
95
96
  /**
97
   * rewrites for n include:
98
   * - (union_max A emptybag) = A
99
   * - (union_max emptybag A) = A
100
   * - (union_max A A) = A
101
   * - (union_max A (union_max A B)) = (union_max A B)
102
   * - (union_max A (union_max B A)) = (union_max B A)
103
   * - (union_max (union_max A B) A) = (union_max A B)
104
   * - (union_max (union_max B A) A) = (union_max B A)
105
   * - (union_max A (union_disjoint A B)) = (union_disjoint A B)
106
   * - (union_max A (union_disjoint B A)) = (union_disjoint B A)
107
   * - (union_max (union_disjoint A B) A) = (union_disjoint A B)
108
   * - (union_max (union_disjoint B A) A) = (union_disjoint B A)
109
   * - otherwise = n
110
   */
111
  BagsRewriteResponse rewriteUnionMax(const TNode& n) const;
112
113
  /**
114
   * rewrites for n include:
115
   * - (union_disjoint A emptybag) = A
116
   * - (union_disjoint emptybag A) = A
117
   * - (union_disjoint (union_max A B) (intersection_min A B)) =
118
   *         (union_disjoint A B) // sum(a,b) = max(a,b) + min(a,b)
119
   * - other permutations of the above like swapping A and B, or swapping
120
   *   intersection_min and union_max
121
   * - otherwise = n
122
   */
123
  BagsRewriteResponse rewriteUnionDisjoint(const TNode& n) const;
124
125
  /**
126
   * rewrites for n include:
127
   * - (intersection_min A emptybag) = emptybag
128
   * - (intersection_min emptybag A) = emptybag
129
   * - (intersection_min A A) = A
130
   * - (intersection_min A (union_disjoint A B)) = A
131
   * - (intersection_min A (union_disjoint B A)) = A
132
   * - (intersection_min (union_disjoint A B) A) = A
133
   * - (intersection_min (union_disjoint B A) A) = A
134
   * - (intersection_min A (union_max A B)) = A
135
   * - (intersection_min A (union_max B A)) = A
136
   * - (intersection_min (union_max A B) A) = A
137
   * - (intersection_min (union_max B A) A) = A
138
   * - otherwise = n
139
   */
140
  BagsRewriteResponse rewriteIntersectionMin(const TNode& n) const;
141
142
  /**
143
   * rewrites for n include:
144
   * - (difference_subtract A emptybag) = A
145
   * - (difference_subtract emptybag A) = emptybag
146
   * - (difference_subtract A A) = emptybag
147
   * - (difference_subtract (union_disjoint A B) A) = B
148
   * - (difference_subtract (union_disjoint B A) A) = B
149
   * - (difference_subtract A (union_disjoint A B)) = emptybag
150
   * - (difference_subtract A (union_disjoint B A)) = emptybag
151
   * - (difference_subtract A (union_max A B)) = emptybag
152
   * - (difference_subtract A (union_max B A)) = emptybag
153
   * - (difference_subtract (intersection_min A B) A) = emptybag
154
   * - (difference_subtract (intersection_min B A) A) = emptybag
155
   * - otherwise = n
156
   */
157
  BagsRewriteResponse rewriteDifferenceSubtract(const TNode& n) const;
158
159
  /**
160
   * rewrites for n include:
161
   * - (difference_remove A emptybag) = A
162
   * - (difference_remove emptybag A) = emptybag
163
   * - (difference_remove A A) = emptybag
164
   * - (difference_remove A (union_disjoint A B)) = emptybag
165
   * - (difference_remove A (union_disjoint B A)) = emptybag
166
   * - (difference_remove A (union_max A B)) = emptybag
167
   * - (difference_remove A (union_max B A)) = emptybag
168
   * - (difference_remove (intersection_min A B) A) = emptybag
169
   * - (difference_remove (intersection_min B A) A) = emptybag
170
   * - otherwise = n
171
   */
172
  BagsRewriteResponse rewriteDifferenceRemove(const TNode& n) const;
173
  /**
174
   * rewrites for n include:
175
   * - (bag.choose (bag x c)) = x where c is a constant > 0
176
   * - otherwise = n
177
   */
178
  BagsRewriteResponse rewriteChoose(const TNode& n) const;
179
  /**
180
   * rewrites for n include:
181
   * - (bag.card (bag x c)) = c where c is a constant > 0
182
   * - (bag.card (union-disjoint A B)) = (+ (bag.card A) (bag.card B))
183
   * - otherwise = n
184
   */
185
  BagsRewriteResponse rewriteCard(const TNode& n) const;
186
187
  /**
188
   * rewrites for n include:
189
   * - (bag.is_singleton (bag x c)) = (c == 1)
190
   */
191
  BagsRewriteResponse rewriteIsSingleton(const TNode& n) const;
192
193
  /**
194
   *  rewrites for n include:
195
   *  - (bag.from_set (singleton (singleton_op Int) x)) = (bag x 1)
196
   */
197
  BagsRewriteResponse rewriteFromSet(const TNode& n) const;
198
199
  /**
200
   *  rewrites for n include:
201
   *  - (bag.to_set (bag x n)) = (singleton (singleton_op T) x)
202
   *     where n is a positive constant and T is the type of the bag's elements
203
   */
204
  BagsRewriteResponse rewriteToSet(const TNode& n) const;
205
206
  /**
207
   *  rewrites for n include:
208
   *  - (= A A) = true
209
   *  - (= A B) = false if A and B are different bag constants
210
   *  - (= B A) = (= A B) if A < B and at least one of A or B is not a constant
211
   */
212
  BagsRewriteResponse postRewriteEqual(const TNode& n) const;
213
214
 private:
215
  /** Reference to the rewriter statistics. */
216
  NodeManager* d_nm;
217
  Node d_zero;
218
  Node d_one;
219
  /** Reference to the rewriter statistics. */
220
  HistogramStat<Rewrite>* d_statistics;
221
}; /* class TheoryBagsRewriter */
222
223
}  // namespace bags
224
}  // namespace theory
225
}  // namespace cvc5
226
227
#endif /* CVC5__THEORY__BAGS__THEORY_BAGS_REWRITER_H */