var non_converting_unary = makePredicate("! typeof void");
def(AST_UnaryPrefix, function(compressor, ignore_side_effects, cached, depth) {
var e = this.expression;
+ var op = this.operator;
// Function would be evaluated to an array and so typeof would
// incorrectly return 'object'. Hence making is a special case.
if (compressor.option("typeofs")
- && this.operator == "typeof"
+ && op == "typeof"
&& (e instanceof AST_Lambda
|| e instanceof AST_SymbolRef
&& e.fixed_value() instanceof AST_Lambda)) {
return typeof function(){};
}
- if (!non_converting_unary[this.operator]) depth++;
+ if (!non_converting_unary[op]) depth++;
var v = e._eval(compressor, ignore_side_effects, cached, depth);
- if (v === this.expression) return this;
- switch (this.operator) {
+ if (v === e) {
+ if (ignore_side_effects && op == "void") return void 0;
+ return this;
+ }
+ switch (op) {
case "!": return !v;
case "typeof":
// typeof <RegExp> returns "object" or "function" on different platforms
if (!(e instanceof AST_SymbolRef)) return this;
var refs = e.definition().references;
if (refs[refs.length - 1] !== e) return this;
- return HOP(e, "_eval") ? +(this.operator[0] + 1) + +v : v;
+ return HOP(e, "_eval") ? +(op[0] + 1) + +v : v;
}
return this;
});
init = fixed;
}
} else {
- var ev = fixed.evaluate(compressor);
- if (ev !== fixed && (!(ev instanceof RegExp)
- || compressor.option("unsafe_regexp") && !def.cross_loop && same_scope(def))) {
+ var ev = fixed.evaluate(compressor, true);
+ if (ev !== fixed
+ && typeof ev != "function"
+ && (typeof ev != "object"
+ || ev instanceof RegExp
+ && compressor.option("unsafe_regexp")
+ && !def.cross_loop && same_scope(def))) {
init = make_node_from_constant(ev, fixed);
}
}