@@ -21,18 +21,19 @@ import Simplify.desugarIdent
21
21
* out (nested) if with equivalent branches wrt to isSimilar. For example:
22
22
* - if (b) exp else exp → b; exp
23
23
* - if (b1) e1 else if (b2) e1 else e2 → if (b1 || b2) e1 else e2
24
+ * - if(!b) e1 else e2 → if(b) e2 else e1
24
25
*
25
26
* - Constant propagation over pattern matching.
26
27
*
27
- * @author DarkDimius, OlivierBlanvillain
28
+ * @author DarkDimius, OlivierBlanvillain, gan74
28
29
*/
29
30
class ConstantFold (val simplifyPhase : Simplify ) extends Optimisation {
30
31
import ast .tpd ._
31
32
32
33
def visitor (implicit ctx : Context ) = NoVisitor
33
34
def clear (): Unit = ()
34
35
35
- def transformer (implicit ctx : Context ): Tree => Tree = { x => preEval(x) match {
36
+ def transformer (implicit ctx : Context ): Tree => Tree = {
36
37
// TODO: include handling of isInstanceOf similar to one in IsInstanceOfEvaluator
37
38
// TODO: include methods such as Int.int2double(see ./tests/pos/harmonize.scala)
38
39
case If (cond1, thenp, elsep) if isSimilar(thenp, elsep) =>
@@ -75,7 +76,7 @@ import Simplify.desugarIdent
75
76
// isBool(ift.tpe) && !elsep.const.booleanValue =>
76
77
// cond.select(defn.Boolean_&&).appliedTo(elsep)
77
78
// the other case ins't handled intentionally. See previous case for explanation
78
-
79
+
79
80
case If (t @ Select (recv, _), thenp, elsep) if t.symbol eq defn.Boolean_! =>
80
81
If (recv, elsep, thenp)
81
82
@@ -141,6 +142,15 @@ import Simplify.desugarIdent
141
142
// Block(List(lhs),
142
143
// ref(defn.throwMethod).appliedTo(New(defn.ArithmeticExceptionClass.typeRef, defn.ArithmeticExceptionClass_stringConstructor, Literal(Constant("/ by zero")) :: Nil)))
143
144
145
+ case (l : Literal , r : Literal ) =>
146
+ (l.tpe.widenTermRefExpr, r.tpe.widenTermRefExpr) match {
147
+ case (ConstantType (_), ConstantType (_)) =>
148
+ val s = ConstFold .apply(t)
149
+ if ((s ne null ) && s.tpe.isInstanceOf [ConstantType ]) Literal (s.tpe.asInstanceOf [ConstantType ].value)
150
+ else t
151
+ case _ => t
152
+ }
153
+
144
154
case _ => t
145
155
}
146
156
@@ -157,26 +167,10 @@ import Simplify.desugarIdent
157
167
158
168
case t : Literal => t
159
169
case t : CaseDef => t
160
- case t if ! isPureExpr(t) => t
161
- case t =>
162
- val s = ConstFold .apply(t)
163
- if ((s ne null ) && s.tpe.isInstanceOf [ConstantType ]) {
164
- val constant = s.tpe.asInstanceOf [ConstantType ].value
165
- Literal (constant)
166
- } else t
167
- }
170
+ case t => t
168
171
}
169
172
170
- def preEval (t : Tree )(implicit ctx : Context ) = {
171
- if (t.isInstanceOf [Literal ] || t.isInstanceOf [CaseDef ] || ! isPureExpr(t)) t
172
- else {
173
- val s = ConstFold .apply(t)
174
- if ((s ne null ) && s.tpe.isInstanceOf [ConstantType ]) {
175
- val constant = s.tpe.asInstanceOf [ConstantType ].value
176
- Literal (constant)
177
- } else t
178
- }
179
- }
173
+
180
174
181
175
def isSimilar (t1 : Tree , t2 : Tree )(implicit ctx : Context ): Boolean = t1 match {
182
176
case t1 : Apply =>
0 commit comments