enhance if_return (#4097)
This commit is contained in:
@@ -2113,18 +2113,22 @@ merge(Compressor.prototype, {
|
|||||||
eliminate_spurious_blocks(stat.body);
|
eliminate_spurious_blocks(stat.body);
|
||||||
[].splice.apply(statements, [i, 1].concat(stat.body));
|
[].splice.apply(statements, [i, 1].concat(stat.body));
|
||||||
i += stat.body.length;
|
i += stat.body.length;
|
||||||
} else if (stat instanceof AST_EmptyStatement) {
|
continue;
|
||||||
CHANGED = true;
|
}
|
||||||
statements.splice(i, 1);
|
if (stat instanceof AST_Directive) {
|
||||||
} else if (stat instanceof AST_Directive) {
|
if (member(stat.value, seen_dirs)) {
|
||||||
if (!member(stat.value, seen_dirs)) {
|
|
||||||
i++;
|
|
||||||
seen_dirs.push(stat.value);
|
|
||||||
} else {
|
|
||||||
CHANGED = true;
|
CHANGED = true;
|
||||||
statements.splice(i, 1);
|
statements.splice(i, 1);
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
} else i++;
|
seen_dirs.push(stat.value);
|
||||||
|
}
|
||||||
|
if (stat instanceof AST_EmptyStatement) {
|
||||||
|
CHANGED = true;
|
||||||
|
statements.splice(i, 1);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
i++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2295,12 +2299,32 @@ merge(Compressor.prototype, {
|
|||||||
return !value || value instanceof AST_UnaryPrefix && value.operator == "void";
|
return !value || value instanceof AST_UnaryPrefix && value.operator == "void";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function is_last_statement(body, stat) {
|
||||||
|
var index = body.lastIndexOf(stat);
|
||||||
|
if (index < 0) return false;
|
||||||
|
while (++index < body.length) {
|
||||||
|
if (!is_declaration(body[index])) return false;
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
function match_target(target) {
|
||||||
|
var block = self, stat, level = 0;
|
||||||
|
do {
|
||||||
|
do {
|
||||||
|
if (block === target) return true;
|
||||||
|
block = compressor.parent(level++);
|
||||||
|
} while (block instanceof AST_If && (stat = block));
|
||||||
|
} while (block instanceof AST_BlockStatement && is_last_statement(block.body, stat));
|
||||||
|
}
|
||||||
|
|
||||||
function can_merge_flow(ab) {
|
function can_merge_flow(ab) {
|
||||||
if (!ab) return false;
|
if (ab instanceof AST_Return) return in_lambda && is_return_void(ab.value);
|
||||||
var lct = ab instanceof AST_LoopControl ? compressor.loopcontrol_target(ab) : null;
|
if (!(ab instanceof AST_LoopControl)) return false;
|
||||||
return ab instanceof AST_Return && in_lambda && is_return_void(ab.value)
|
var lct = compressor.loopcontrol_target(ab);
|
||||||
|| ab instanceof AST_Continue && self === loop_body(lct)
|
if (ab instanceof AST_Continue) return match_target(loop_body(lct));
|
||||||
|| ab instanceof AST_Break && lct instanceof AST_BlockStatement && self === lct;
|
if (lct instanceof AST_IterationStatement) return false;
|
||||||
|
return match_target(lct);
|
||||||
}
|
}
|
||||||
|
|
||||||
function extract_functions() {
|
function extract_functions() {
|
||||||
@@ -2327,20 +2351,14 @@ merge(Compressor.prototype, {
|
|||||||
|
|
||||||
function next_index(i) {
|
function next_index(i) {
|
||||||
for (var j = i + 1; j < statements.length; j++) {
|
for (var j = i + 1; j < statements.length; j++) {
|
||||||
var stat = statements[j];
|
if (!is_declaration(statements[j])) break;
|
||||||
if (!(stat instanceof AST_Var && declarations_only(stat))) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
|
|
||||||
function prev_index(i) {
|
function prev_index(i) {
|
||||||
for (var j = i; --j >= 0;) {
|
for (var j = i; --j >= 0;) {
|
||||||
var stat = statements[j];
|
if (!is_declaration(statements[j])) break;
|
||||||
if (!(stat instanceof AST_Var && declarations_only(stat))) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return j;
|
return j;
|
||||||
}
|
}
|
||||||
@@ -2383,6 +2401,10 @@ merge(Compressor.prototype, {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function is_declaration(stat) {
|
||||||
|
return stat instanceof AST_Defun || stat instanceof AST_Var && declarations_only(stat);
|
||||||
|
}
|
||||||
|
|
||||||
function sequencesize(statements, compressor) {
|
function sequencesize(statements, compressor) {
|
||||||
if (statements.length < 2) return;
|
if (statements.length < 2) return;
|
||||||
var seq = [], n = 0;
|
var seq = [], n = 0;
|
||||||
@@ -2399,8 +2421,7 @@ merge(Compressor.prototype, {
|
|||||||
var body = stat.body;
|
var body = stat.body;
|
||||||
if (seq.length > 0) body = body.drop_side_effect_free(compressor);
|
if (seq.length > 0) body = body.drop_side_effect_free(compressor);
|
||||||
if (body) merge_sequence(seq, body);
|
if (body) merge_sequence(seq, body);
|
||||||
} else if (stat instanceof AST_Definitions && declarations_only(stat)
|
} else if (is_declaration(stat)) {
|
||||||
|| stat instanceof AST_Defun) {
|
|
||||||
statements[n++] = stat;
|
statements[n++] = stat;
|
||||||
} else {
|
} else {
|
||||||
push_seq();
|
push_seq();
|
||||||
|
|||||||
@@ -594,3 +594,72 @@ iife_if_return_simple: {
|
|||||||
}
|
}
|
||||||
expect_stdout: "PASS"
|
expect_stdout: "PASS"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
nested_if_break: {
|
||||||
|
options = {
|
||||||
|
if_return: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
for (var i = 0; i < 3; i++)
|
||||||
|
L1: if ("number" == typeof i) {
|
||||||
|
if (0 === i) break L1;
|
||||||
|
console.log(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
for (var i = 0; i < 3; i++)
|
||||||
|
L1: if ("number" == typeof i)
|
||||||
|
if (0 !== i) console.log(i);
|
||||||
|
}
|
||||||
|
expect_stdout: [
|
||||||
|
"1",
|
||||||
|
"2",
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
nested_if_continue: {
|
||||||
|
options = {
|
||||||
|
conditionals: true,
|
||||||
|
if_return: true,
|
||||||
|
join_vars: true,
|
||||||
|
loops: true,
|
||||||
|
}
|
||||||
|
input: {
|
||||||
|
function f(n) {
|
||||||
|
var i = 0;
|
||||||
|
do {
|
||||||
|
if ("number" == typeof n) {
|
||||||
|
if (0 === n) {
|
||||||
|
console.log("even", i);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (1 === n) {
|
||||||
|
console.log("odd", i);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
} while (0 <= (n -= 2));
|
||||||
|
}
|
||||||
|
f(37);
|
||||||
|
f(42);
|
||||||
|
}
|
||||||
|
expect: {
|
||||||
|
function f(n) {
|
||||||
|
for (var i = 0;
|
||||||
|
"number" == typeof n
|
||||||
|
&& (0 !== n
|
||||||
|
? 1 !== n
|
||||||
|
? i++
|
||||||
|
: console.log("odd", i)
|
||||||
|
: console.log("even", i)),
|
||||||
|
0 <= (n -= 2););
|
||||||
|
}
|
||||||
|
f(37);
|
||||||
|
f(42);
|
||||||
|
}
|
||||||
|
expect_stdout: [
|
||||||
|
"odd 18",
|
||||||
|
"even 21",
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user