@@ -2452,7 +2452,7 @@ Compressor.prototype.compress = function(node) {
|
|||||||
|
|
||||||
function is_last_node(node, parent) {
|
function is_last_node(node, parent) {
|
||||||
if (node instanceof AST_Await) return true;
|
if (node instanceof AST_Await) return true;
|
||||||
if (node.TYPE == "Binary") return node.operator == "in" && !is_object(node.right);
|
if (node.TYPE == "Binary") return !can_drop_op(node.operator, node.right);
|
||||||
if (node instanceof AST_Call) {
|
if (node instanceof AST_Call) {
|
||||||
var def, fn = node.expression;
|
var def, fn = node.expression;
|
||||||
if (fn instanceof AST_SymbolRef) {
|
if (fn instanceof AST_SymbolRef) {
|
||||||
@@ -5551,7 +5551,7 @@ Compressor.prototype.compress = function(node) {
|
|||||||
def(AST_Binary, function(compressor) {
|
def(AST_Binary, function(compressor) {
|
||||||
return this.left.has_side_effects(compressor)
|
return this.left.has_side_effects(compressor)
|
||||||
|| this.right.has_side_effects(compressor)
|
|| this.right.has_side_effects(compressor)
|
||||||
|| this.operator == "in" && !is_object(this.right);
|
|| !can_drop_op(this.operator, this.right);
|
||||||
});
|
});
|
||||||
def(AST_Block, function(compressor) {
|
def(AST_Block, function(compressor) {
|
||||||
return any(this.body, compressor);
|
return any(this.body, compressor);
|
||||||
@@ -5705,7 +5705,7 @@ Compressor.prototype.compress = function(node) {
|
|||||||
def(AST_Binary, function(compressor) {
|
def(AST_Binary, function(compressor) {
|
||||||
return this.left.may_throw(compressor)
|
return this.left.may_throw(compressor)
|
||||||
|| this.right.may_throw(compressor)
|
|| this.right.may_throw(compressor)
|
||||||
|| this.operator == "in" && !is_object(this.right);
|
|| !can_drop_op(this.operator, this.right);
|
||||||
});
|
});
|
||||||
def(AST_Block, function(compressor) {
|
def(AST_Block, function(compressor) {
|
||||||
return any(this.body, compressor);
|
return any(this.body, compressor);
|
||||||
@@ -5822,7 +5822,7 @@ Compressor.prototype.compress = function(node) {
|
|||||||
def(AST_Binary, function(scope) {
|
def(AST_Binary, function(scope) {
|
||||||
return this.left.is_constant_expression(scope)
|
return this.left.is_constant_expression(scope)
|
||||||
&& this.right.is_constant_expression(scope)
|
&& this.right.is_constant_expression(scope)
|
||||||
&& (this.operator != "in" || is_object(this.right));
|
&& can_drop_op(this.operator, this.right);
|
||||||
});
|
});
|
||||||
def(AST_Class, function(scope) {
|
def(AST_Class, function(scope) {
|
||||||
var base = this.extends;
|
var base = this.extends;
|
||||||
@@ -8533,7 +8533,7 @@ Compressor.prototype.compress = function(node) {
|
|||||||
var left = this.left;
|
var left = this.left;
|
||||||
var right = this.right;
|
var right = this.right;
|
||||||
var op = this.operator;
|
var op = this.operator;
|
||||||
if (op == "in" && !is_object(right)) {
|
if (!can_drop_op(op, right)) {
|
||||||
var lhs = left.drop_side_effect_free(compressor, first_in_statement);
|
var lhs = left.drop_side_effect_free(compressor, first_in_statement);
|
||||||
if (lhs === left) return this;
|
if (lhs === left) return this;
|
||||||
var node = this.clone();
|
var node = this.clone();
|
||||||
@@ -11202,6 +11202,18 @@ Compressor.prototype.compress = function(node) {
|
|||||||
|| node instanceof AST_Object;
|
|| node instanceof AST_Object;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function can_drop_op(op, rhs) {
|
||||||
|
switch (op) {
|
||||||
|
case "in":
|
||||||
|
return is_object(rhs);
|
||||||
|
case "instanceof":
|
||||||
|
if (rhs instanceof AST_SymbolRef) rhs = rhs.fixed_value();
|
||||||
|
return is_lambda(rhs);
|
||||||
|
default:
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
function is_primitive(compressor, node) {
|
function is_primitive(compressor, node) {
|
||||||
if (node.is_constant()) return true;
|
if (node.is_constant()) return true;
|
||||||
if (node instanceof AST_Assign) return node.operator != "=" || is_primitive(compressor, node.right);
|
if (node instanceof AST_Assign) return node.operator != "=" || is_primitive(compressor, node.right);
|
||||||
@@ -11708,6 +11720,12 @@ Compressor.prototype.compress = function(node) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
case "instanceof":
|
||||||
|
if (is_lambda(self.right)) return make_sequence(self, [
|
||||||
|
self,
|
||||||
|
make_node(AST_False, self),
|
||||||
|
]).optimize(compressor);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
if (!(parent instanceof AST_UnaryPrefix && parent.operator == "delete")) {
|
if (!(parent instanceof AST_UnaryPrefix && parent.operator == "delete")) {
|
||||||
if (self.left instanceof AST_Number && !self.right.is_constant()) switch (self.operator) {
|
if (self.left instanceof AST_Number && !self.right.is_constant()) switch (self.operator) {
|
||||||
|
|||||||
@@ -260,6 +260,15 @@ function OutputStream(options) {
|
|||||||
|
|
||||||
var require_semicolon = makePredicate("( [ + * / - , .");
|
var require_semicolon = makePredicate("( [ + * / - , .");
|
||||||
|
|
||||||
|
function require_space(prev, ch, str) {
|
||||||
|
return is_identifier_char(prev) && (is_identifier_char(ch) || ch == "\\")
|
||||||
|
|| (ch == "/" && ch == prev)
|
||||||
|
|| ((ch == "+" || ch == "-") && ch == last)
|
||||||
|
|| last == "--" && ch == ">"
|
||||||
|
|| last == "!" && str == "--"
|
||||||
|
|| prev == "/" && (str == "in" || str == "instanceof");
|
||||||
|
}
|
||||||
|
|
||||||
var print = options.beautify
|
var print = options.beautify
|
||||||
|| options.comments
|
|| options.comments
|
||||||
|| options.max_line_len
|
|| options.max_line_len
|
||||||
@@ -312,12 +321,7 @@ function OutputStream(options) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (might_need_space) {
|
if (might_need_space) {
|
||||||
if (is_identifier_char(prev) && (is_identifier_char(ch) || ch == "\\")
|
if (require_space(prev, ch, str)) {
|
||||||
|| (ch == "/" && ch == prev)
|
|
||||||
|| ((ch == "+" || ch == "-") && ch == last)
|
|
||||||
|| str == "--" && last == "!"
|
|
||||||
|| str == "in" && prev == "/"
|
|
||||||
|| last == "--" && ch == ">") {
|
|
||||||
output += " ";
|
output += " ";
|
||||||
current_col++;
|
current_col++;
|
||||||
}
|
}
|
||||||
@@ -355,14 +359,7 @@ function OutputStream(options) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (might_need_space) {
|
if (might_need_space) {
|
||||||
if (is_identifier_char(prev) && (is_identifier_char(ch) || ch == "\\")
|
if (require_space(prev, ch, str)) output += " ";
|
||||||
|| (ch == "/" && ch == prev)
|
|
||||||
|| ((ch == "+" || ch == "-") && ch == last)
|
|
||||||
|| str == "--" && last == "!"
|
|
||||||
|| str == "in" && prev == "/"
|
|
||||||
|| last == "--" && ch == ">") {
|
|
||||||
output += " ";
|
|
||||||
}
|
|
||||||
if (prev != "<" || str != "!") might_need_space = false;
|
if (prev != "<" || str != "!") might_need_space = false;
|
||||||
}
|
}
|
||||||
output += str;
|
output += str;
|
||||||
@@ -1819,9 +1816,6 @@ function OutputStream(options) {
|
|||||||
case "\u2029": return "\\u2029";
|
case "\u2029": return "\\u2029";
|
||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
var p = output.parent();
|
|
||||||
if (p instanceof AST_Binary && /^in/.test(p.operator) && p.left === this)
|
|
||||||
output.print(" ");
|
|
||||||
});
|
});
|
||||||
|
|
||||||
function force_statement(stat, output) {
|
function force_statement(stat, output) {
|
||||||
|
|||||||
@@ -1293,6 +1293,21 @@ functions_inner_var: {
|
|||||||
node_version: ">=8"
|
node_version: ">=8"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
instanceof_lambda: {
|
||||||
|
options = {
|
||||||
|
evaluate: true,
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
console.log(42 instanceof async function() {});
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
console.log(false);
|
||||||
|
}
|
||||||
|
expect_stdout: "false"
|
||||||
|
node_version: ">=8"
|
||||||
|
}
|
||||||
|
|
||||||
issue_4335_1: {
|
issue_4335_1: {
|
||||||
options = {
|
options = {
|
||||||
inline: true,
|
inline: true,
|
||||||
|
|||||||
@@ -1266,6 +1266,23 @@ keep_fnames: {
|
|||||||
node_version: ">=4"
|
node_version: ">=4"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
instanceof_lambda: {
|
||||||
|
options = {
|
||||||
|
evaluate: true,
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
"use strict";
|
||||||
|
console.log(42 instanceof class {});
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
"use strict";
|
||||||
|
console.log(false);
|
||||||
|
}
|
||||||
|
expect_stdout: "false"
|
||||||
|
node_version: ">=4"
|
||||||
|
}
|
||||||
|
|
||||||
issue_805_1: {
|
issue_805_1: {
|
||||||
options = {
|
options = {
|
||||||
inline: true,
|
inline: true,
|
||||||
|
|||||||
@@ -907,6 +907,20 @@ chained_side_effects: {
|
|||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
instanceof_lambda: {
|
||||||
|
options = {
|
||||||
|
evaluate: true,
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
console.log(42 instanceof function() {});
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
console.log(false);
|
||||||
|
}
|
||||||
|
expect_stdout: "false"
|
||||||
|
}
|
||||||
|
|
||||||
issue_1649: {
|
issue_1649: {
|
||||||
options = {
|
options = {
|
||||||
evaluate: true,
|
evaluate: true,
|
||||||
|
|||||||
@@ -147,7 +147,7 @@ relational: {
|
|||||||
"bar" >= "bar";
|
"bar" >= "bar";
|
||||||
}
|
}
|
||||||
expect: {
|
expect: {
|
||||||
bar();
|
0 instanceof bar();
|
||||||
bar();
|
bar();
|
||||||
bar(), bar();
|
bar(), bar();
|
||||||
bar();
|
bar();
|
||||||
|
|||||||
@@ -50,6 +50,22 @@ regexp_properties: {
|
|||||||
expect_stdout: "abc true false 0 false"
|
expect_stdout: "abc true false 0 false"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
instanceof_1: {
|
||||||
|
input: {
|
||||||
|
console.log(/foo/ instanceof RegExp);
|
||||||
|
}
|
||||||
|
expect_exact: "console.log(/foo/ instanceof RegExp);"
|
||||||
|
expect_stdout: "true"
|
||||||
|
}
|
||||||
|
|
||||||
|
instanceof_2: {
|
||||||
|
input: {
|
||||||
|
console.log(42 + /foo/ instanceof Object);
|
||||||
|
}
|
||||||
|
expect_exact: "console.log(42+/foo/ instanceof Object);"
|
||||||
|
expect_stdout: "false"
|
||||||
|
}
|
||||||
|
|
||||||
issue_3434_1: {
|
issue_3434_1: {
|
||||||
options = {
|
options = {
|
||||||
evaluate: true,
|
evaluate: true,
|
||||||
|
|||||||
@@ -645,3 +645,56 @@ issue_4751: {
|
|||||||
}
|
}
|
||||||
expect_stdout: "PASS"
|
expect_stdout: "PASS"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
drop_instanceof: {
|
||||||
|
options = {
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
42 instanceof function() {};
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
expect_stdout: "PASS"
|
||||||
|
}
|
||||||
|
|
||||||
|
drop_instanceof_reference: {
|
||||||
|
options = {
|
||||||
|
reduce_vars: true,
|
||||||
|
side_effects: true,
|
||||||
|
toplevel: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
function f() {}
|
||||||
|
42 instanceof f;
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
function f() {}
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
expect_stdout: "PASS"
|
||||||
|
}
|
||||||
|
|
||||||
|
retain_instanceof: {
|
||||||
|
options = {
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
try {
|
||||||
|
42 instanceof "foo";
|
||||||
|
} catch (e) {
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
try {
|
||||||
|
0 instanceof "foo";
|
||||||
|
} catch (e) {
|
||||||
|
console.log("PASS");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
expect_stdout: "PASS"
|
||||||
|
}
|
||||||
|
|||||||
@@ -934,6 +934,21 @@ drop_unused_call: {
|
|||||||
node_version: ">=4"
|
node_version: ">=4"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
instanceof_lambda: {
|
||||||
|
options = {
|
||||||
|
evaluate: true,
|
||||||
|
side_effects: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
console.log(42 instanceof function*() {});
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
console.log(false);
|
||||||
|
}
|
||||||
|
expect_stdout: "false"
|
||||||
|
node_version: ">=4"
|
||||||
|
}
|
||||||
|
|
||||||
issue_4454_1: {
|
issue_4454_1: {
|
||||||
rename = false
|
rename = false
|
||||||
options = {
|
options = {
|
||||||
|
|||||||
@@ -253,7 +253,7 @@ BINARY_OPS = BINARY_OPS.concat(BINARY_OPS);
|
|||||||
if (SUPPORT.exponentiation) BINARY_OPS.push("**");
|
if (SUPPORT.exponentiation) BINARY_OPS.push("**");
|
||||||
BINARY_OPS = BINARY_OPS.concat(BINARY_OPS);
|
BINARY_OPS = BINARY_OPS.concat(BINARY_OPS);
|
||||||
BINARY_OPS = BINARY_OPS.concat(BINARY_OPS);
|
BINARY_OPS = BINARY_OPS.concat(BINARY_OPS);
|
||||||
BINARY_OPS.push(" in ");
|
BINARY_OPS.push(" in ", " instanceof ");
|
||||||
|
|
||||||
var ASSIGNMENTS = [ "=" ];
|
var ASSIGNMENTS = [ "=" ];
|
||||||
ASSIGNMENTS = ASSIGNMENTS.concat(ASSIGNMENTS);
|
ASSIGNMENTS = ASSIGNMENTS.concat(ASSIGNMENTS);
|
||||||
@@ -2009,7 +2009,7 @@ function createBinaryOp(noComma, canThrow) {
|
|||||||
var op;
|
var op;
|
||||||
do {
|
do {
|
||||||
op = BINARY_OPS[rng(BINARY_OPS.length)];
|
op = BINARY_OPS[rng(BINARY_OPS.length)];
|
||||||
} while (noComma && op == "," || !canThrow && op == " in ");
|
} while (noComma && op == "," || !canThrow && /^ in/.test(op));
|
||||||
return op;
|
return op;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user