various random optimisations

This commit is contained in:
Sebastian McKenzie 2015-04-26 21:04:06 +01:00
parent b695369126
commit 470ebf3a46
14 changed files with 75 additions and 61 deletions

View File

@ -508,7 +508,7 @@ export default class File {
this.log.debug("End set AST");
this.log.debug("Start prepass");
//this.checkPath(this.path);
this.checkPath(this.path);
this.log.debug("End prepass");
this.log.debug("Start module formatter init");

View File

@ -10,6 +10,10 @@ export default function (exports, opts) {
return t.assignmentExpression("=", left, right);
};
exports.shouldVisit = function (node) {
return node.operator && (node.operator === opts.operator || node.operator === opts.operator + "=");
};
exports.ExpressionStatement = function (node, parent, scope, file) {
// hit the `AssignmentExpression` one below
if (this.isCompletionRecord()) return;

View File

@ -26,7 +26,11 @@ export default function (decorators, scope) {
[ref]
));
decorator.expression = t.sequenceExpression(nodes);
if (nodes.length === 1) {
decorator.expression = nodes[0];
} else {
decorator.expression = t.sequenceExpression(nodes);
}
}
return decorators;

View File

@ -39,7 +39,6 @@ var wrap = function (state, method, id, scope) {
return template;
} else {
method.id = id;
return method;
}
};
@ -96,7 +95,7 @@ export function custom(node, id, scope) {
export function property(node, file, scope) {
var key = t.toComputedKey(node, node.key);
if (!t.isLiteral(key)) return node; // we can't set a function id with this
if (!t.isLiteral(key)) return; // we can't set a function id with this
var name = t.toIdentifier(key.value);
if (name === "eval" || name === "arguments") name = "_" + name;
@ -109,7 +108,7 @@ export function property(node, file, scope) {
export function bare(node, parent, scope) {
// has an `id` so we don't need to infer one
if (node.id) return node;
if (node.id) return;
var id;
if (t.isProperty(parent) && parent.kind === "init" && (!parent.computed || t.isLiteral(parent.key))) {
@ -119,7 +118,7 @@ export function bare(node, parent, scope) {
// var foo = function () {};
id = parent.id;
} else {
return node;
return;
}
var name;
@ -128,7 +127,7 @@ export function bare(node, parent, scope) {
} else if (t.isIdentifier(id)) {
name = id.name;
} else {
return node;
return;
}
name = t.toIdentifier(name);

View File

@ -8,11 +8,12 @@ import traverse from "../traversal";
export default class TransformerPass {
constructor(file: File, transformer: Transformer) {
this.transformer = transformer;
this.handlers = transformer.handlers;
this.skipKey = transformer.skipKey;
this.file = file;
this.ran = false;
this.shouldTransform = !transformer.shouldVisit;
this.transformer = transformer;
this.handlers = transformer.handlers;
this.skipKey = transformer.skipKey;
this.file = file;
this.ran = false;
}
canTransform(): boolean {
@ -43,12 +44,14 @@ export default class TransformerPass {
}
checkPath(path: TraversalPath): boolean {
var shouldVisit = this.transformer.shouldVisit;
if (!shouldVisit) return;
if (this.shouldTransform || this.ran) return;
this.shouldTransform = this.transformer.shouldVisit(path.node);
}
transform() {
if (!this.shouldTransform) return;
var file = this.file;
file.log.debug(`Start transformer ${this.transformer.key}`);

View File

@ -26,7 +26,6 @@ export default class Transformer {
this.manipulateOptions = take("manipulateOptions");
this.shouldVisit = take("shouldVisit");
this.metadata = take("metadata") || {};
this.skipKey = `transformer:${transformerKey}:skip`;
this.parser = take("parser");
this.post = take("post");
this.pre = take("pre");
@ -48,7 +47,10 @@ export default class Transformer {
if (!this.shouldVisit) {
var types = Object.keys(this.handlers);
this.shouldVisit = function (node) {
return types.indexOf(node.type) >= 0;
for (var i = 0; i < types.length; i++) {
if (node.type === types[i]) return true;
}
return false;
};
}
}
@ -79,10 +81,6 @@ export default class Transformer {
transformer[type] = fns;
});
transformer.shouldSkip = (path) => {
return path.getData(this.skipKey) === true;
};
return transformer;
}

View File

@ -245,7 +245,7 @@ class ClassTransformer {
if (body.length === 1) return t.toExpression(body[0]);
} else {
// infer class name if this is a nameless class expression
constructor = nameMethod.bare(constructor, this.parent, this.scope);
constructor = nameMethod.bare(constructor, this.parent, this.scope) || constructor;
body.unshift(t.variableDeclaration("var", [
t.variableDeclarator(classRef, constructor)

View File

@ -115,6 +115,5 @@ export default {
"utility.inlineExpressions": require("./utility/inline-expressions"),
"utility.deadCodeElimination": require("./utility/dead-code-elimination"),
flow: require("./other/flow"),
_cleanUp: require("./internal/cleanup")
flow: require("./other/flow")
};

View File

@ -1,30 +0,0 @@
export var SequenceExpression = {
exit(node) {
if (node.expressions.length === 1) {
return node.expressions[0];
} else if (!node.expressions.length) {
this.remove();
}
}
};
export var ExpressionStatement = {
exit(node) {
if (!node.expression) this.remove();
}
};
export var Binary = {
exit(node) {
var right = node.right;
var left = node.left;
if (!left && !right) {
this.remove();
} else if (!left) {
return right;
} else if (!right) {
return left;
}
}
};

View File

@ -1,6 +1,8 @@
import * as strict from "../../helpers/strict";
export function Program(program, parent, scope, file) {
this.stop();
strict.wrap(program, function () {
program.body = file.dynamicImports.concat(program.body);
});

View File

@ -1,5 +1,9 @@
import * as t from "../../../types";
export function shouldVisit(node) {
return node.isType || node.optional || node.implements || node.typeAnnotation || t.isFlow(node);
}
export function Flow(node) {
this.remove();
}

View File

@ -23,6 +23,16 @@ function statementList(key, path, file) {
}
}
export function shouldVisit(node) {
if (node.type !== "BlockStatement") return false;
for (var i = 0; i < node.body.length; i++) {
if (node.body[i].type === "FunctionDeclaration") return true;
}
return false;
}
export function BlockStatement(node, parent, scope, file) {
if ((t.isFunction(parent) && parent.body === node) || t.isExportDeclaration(parent)) {
return;

View File

@ -253,15 +253,32 @@ export default class TraversalPath {
}
remove() {
var removeParent = false;
if (this.parentPath) {
removeParent ||= this.parentPath.isExpressionStatement();
removeParent ||= this.parentPath.isSequenceExpression() && this.parent.expressions.length === 1;
if (removeParent) return this.parentPath.remove();
}
this._remove();
this.removed = true;
var parentPath = this.parentPath;
var parent = this.parent;
if (!parentPath) return;
// we're the child of an expression statement so we should remove the parent
if (parentPath.isExpressionStatement()) {
return parentPath.remove();
}
// we've just removed the second element of a sequence expression so let's turn that sequence
// expression into a regular expression
if (parentPath.isSequenceExpression() && parent.expressions.length === 1) {
parentPath.replaceWith(parent.expressions[0]);
}
// we're in a binary expression, better remove it and replace it with the last expression
if (parentPath.isBinary()) {
if (this.key === "left") {
parentPath.replaceWith(parent.right);
} else { // key === "right"
parentPath.replaceWith(parent.left);
}
}
}
skip() {

View File

@ -78,7 +78,11 @@ export function isType(nodeType, targetType) {
if (nodeType === targetType) return true;
var aliases = t.FLIPPED_ALIAS_KEYS[targetType];
if (aliases) return aliases.indexOf(nodeType) > -1;
if (aliases) {
for (var i = 0; i < aliases.length; i++) {
if (nodeType === aliases[i]) return true;
}
}
return false;
}