inline functions with directives more effectively (#3604)
authorAlex Lam S.L <alexlamsl@gmail.com>
Mon, 25 Nov 2019 17:51:04 +0000 (01:51 +0800)
committerGitHub <noreply@github.com>
Mon, 25 Nov 2019 17:51:04 +0000 (01:51 +0800)
lib/compress.js
test/compress/functions.js

index c195c42..79bf99b 100644 (file)
@@ -2724,6 +2724,14 @@ merge(Compressor.prototype, {
         });
     }
 
+    AST_Lambda.DEFMETHOD("first_statement", function() {
+        var body = this.body;
+        for (var i = 0; i < body.length; i++) {
+            var stat = body[i];
+            if (!(stat instanceof AST_Directive)) return stat;
+        }
+    });
+
     function try_evaluate(compressor, node) {
         var ev = node.evaluate(compressor);
         if (ev === node) return node;
@@ -3098,7 +3106,7 @@ merge(Compressor.prototype, {
             if (fn instanceof AST_Lambda) {
                 if (fn.evaluating) return this;
                 if (fn.name && fn.name.definition().recursive_refs > 0) return this;
-                var stat = fn.body[0];
+                var stat = fn.first_statement();
                 if (!(stat instanceof AST_Return)) return this;
                 var args = eval_args(this.args);
                 if (!args) return this;
@@ -5363,7 +5371,7 @@ merge(Compressor.prototype, {
                 }
             }
         }
-        var stat = is_func && fn.body[0];
+        var stat = is_func && fn.first_statement();
         var can_inline = compressor.option("inline") && !self.is_expr_pure(compressor);
         if (exp === fn && can_inline && stat instanceof AST_Return) {
             var value = stat.value;
index 2af14a6..4f3139b 100644 (file)
@@ -3568,3 +3568,29 @@ pr_3592_2: {
     }
     expect_stdout: "PASS"
 }
+
+inline_use_strict: {
+    options = {
+        evaluate: true,
+        inline: true,
+        reduce_vars: true,
+        sequences: true,
+        side_effects: true,
+        unused: true,
+    }
+    input: {
+        console.log(function() {
+            "use strict";
+            return function() {
+                "use strict";
+                var a = "foo";
+                a += "bar";
+                return a;
+            };
+        }()());
+    }
+    expect: {
+        console.log("foobar");
+    }
+    expect_stdout: "foobar"
+}