Skip to content

Commit

Permalink
Remove unnecessary inner class to make this pass more consistent with…
Browse files Browse the repository at this point in the history
… other compiler passes.

-------------
Created by MOE: https://github.com/google/moe
MOE_MIGRATED_REVID=173941461
  • Loading branch information
tbreisacher authored and brad4d committed Oct 31, 2017
1 parent ffb2649 commit 63a7a96
Showing 1 changed file with 51 additions and 58 deletions.
109 changes: 51 additions & 58 deletions src/com/google/javascript/jscomp/CollapseAnonymousFunctions.java
Expand Up @@ -16,7 +16,6 @@
package com.google.javascript.jscomp; package com.google.javascript.jscomp;


import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.base.Preconditions.checkState;


import com.google.javascript.jscomp.NodeTraversal.AbstractPostOrderCallback; import com.google.javascript.jscomp.NodeTraversal.AbstractPostOrderCallback;
import com.google.javascript.rhino.Node; import com.google.javascript.rhino.Node;
Expand All @@ -39,7 +38,7 @@
* "function f" is block scoped, which may cause issues. * "function f" is block scoped, which may cause issues.
* *
*/ */
class CollapseAnonymousFunctions implements CompilerPass { class CollapseAnonymousFunctions extends AbstractPostOrderCallback implements CompilerPass {
private final AbstractCompiler compiler; private final AbstractCompiler compiler;


public CollapseAnonymousFunctions(AbstractCompiler compiler) { public CollapseAnonymousFunctions(AbstractCompiler compiler) {
Expand All @@ -49,75 +48,69 @@ public CollapseAnonymousFunctions(AbstractCompiler compiler) {


@Override @Override
public void process(Node externs, Node root) { public void process(Node externs, Node root) {
NodeTraversal.traverseEs6(compiler, root, new Callback()); NodeTraversal.traverseEs6(compiler, root, this);
} }


private class Callback extends AbstractPostOrderCallback { @Override
@Override public void visit(NodeTraversal t, Node n, Node parent) {
public void visit(NodeTraversal t, Node n, Node parent) { if (!n.isVar()) {
if (!n.isVar()) { return;
return; }
}

// It is only safe to collapse anonymous functions that appear
// at top-level blocks. In other cases the difference between
// variable and function declarations can lead to problems or
// expose subtle bugs in browser implementation as function
// definitions are added to scopes before the start of execution.


Node grandparent = parent.getParent(); // It is only safe to collapse anonymous functions that appear
if (!(parent.isScript() // at top-level blocks. In other cases the difference between
|| grandparent != null && grandparent.isFunction() && parent.isNormalBlock())) { // variable and function declarations can lead to problems or
return; // expose subtle bugs in browser implementation as function
} // definitions are added to scopes before the start of execution.


// Need to store the next name in case the current name is removed from Node grandparent = parent.getParent();
// the linked list. if (!(parent.isScript()
checkState(n.hasOneChild(), n); || (grandparent != null && grandparent.isFunction() && parent.isNormalBlock()))) {
Node name = n.getFirstChild(); return;
Node value = name.getFirstChild(); }
if (value != null &&
value.isFunction() &&
!isRecursiveFunction(value)) {
Node fnName = value.getFirstChild();
fnName.setString(name.getString());
NodeUtil.copyNameAnnotations(name, fnName);
name.removeChild(value);
parent.replaceChild(n, value);


// Renormalize the code. // Need to store the next name in case the current name is removed from
if (!t.inGlobalScope() && // the linked list.
NodeUtil.isHoistedFunctionDeclaration(value)) { Node name = n.getOnlyChild();
parent.addChildToFront(value.detach()); Node value = name.getFirstChild();
} if (value != null && value.isFunction() && !isRecursiveFunction(value)) {
Node fnName = value.getFirstChild();
fnName.setString(name.getString());
NodeUtil.copyNameAnnotations(name, fnName);
name.removeChild(value);
parent.replaceChild(n, value);


// report changes to both the change scopes // Renormalize the code.
compiler.reportChangeToChangeScope(value); if (!t.inGlobalScope() && NodeUtil.isHoistedFunctionDeclaration(value)) {
t.reportCodeChange(); parent.addChildToFront(value.detach());
} }

// report changes to both the change scopes
compiler.reportChangeToChangeScope(value);
t.reportCodeChange();
}
}

private boolean isRecursiveFunction(Node function) {
Node name = function.getFirstChild();
if (name.getString().isEmpty()) {
return false;
} }
Node args = name.getNext();
Node body = args.getNext();
return containsName(body, name.getString());
}


private boolean isRecursiveFunction(Node function) { private boolean containsName(Node n, String name) {
Node name = function.getFirstChild(); if (n.isName() && n.getString().equals(name)) {
if (name.getString().isEmpty()) { return true;
return false;
}
Node args = name.getNext();
Node body = args.getNext();
return containsName(body, name.getString());
} }


private boolean containsName(Node n, String name) { for (Node child : n.children()) {
if (n.isName() && n.getString().equals(name)) { if (containsName(child, name)) {
return true; return true;
} }

for (Node child : n.children()) {
if (containsName(child, name)) {
return true;
}
}
return false;
} }
return false;
} }
} }

0 comments on commit 63a7a96

Please sign in to comment.