asterixdb-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From buyin...@apache.org
Subject [3/3] incubator-asterixdb git commit: Fix for ASTERIXDB-1018, ASTERIXDB-1017, ASTERIXDB-1019, ASTERIXDB-1020, ASTERIXDB-1029, ASTERIXDB-1030, ASTERIXDB-1034
Date Thu, 31 Dec 2015 05:19:30 GMT
Fix for ASTERIXDB-1018, ASTERIXDB-1017, ASTERIXDB-1019,
ASTERIXDB-1020, ASTERIXDB-1029, ASTERIXDB-1030, ASTERIXDB-1034

1. Inline SubplanOperator input and hence remove SubplanOperator.

2. Use boolean return from initFromSubTree to confirm that the
result should actually be used in IntroduceJoinAccessMethodRule
Prevent accidental attempted cast of null variable
in AbstractIntroduceAccessMethodrule.

Change-Id: Ifc1f844ac6e06e00da3f1618235b6ce9bfd48e9f
Reviewed-on: https://asterix-gerrit.ics.uci.edu/489
Tested-by: Jenkins <jenkins@fulliautomatix.ics.uci.edu>
Reviewed-by: Yingyi Bu <buyingyi@gmail.com>


Project: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/commit/e3e13735
Tree: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/tree/e3e13735
Diff: http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/diff/e3e13735

Branch: refs/heads/master
Commit: e3e13735b760491482ac7dd680dec58c5f635c16
Parents: 4ac9188
Author: Yingyi Bu <yingyi@couchbase.com>
Authored: Wed Dec 30 16:06:04 2015 -0800
Committer: Yingyi Bu <buyingyi@gmail.com>
Committed: Wed Dec 30 21:15:16 2015 -0800

----------------------------------------------------------------------
 .../base/LogicalExpressionDeepCopyVisitor.java  | 153 -----
 .../base/LogicalOperatorDeepCopyVisitor.java    | 490 ---------------
 .../asterix/optimizer/base/RuleCollections.java |  23 +-
 ...oveFreeVariableOperatorOutOfSubplanRule.java |  30 -
 .../asterix/optimizer/rules/FuzzyJoinRule.java  |  67 +-
 .../rules/PushGroupByThroughProduct.java        |  14 +-
 .../optimizer/rules/UnnestToDataScanRule.java   |   3 +-
 .../am/AbstractIntroduceAccessMethodRule.java   |   2 +-
 .../rules/am/IntroduceJoinAccessMethodRule.java |   8 +-
 .../rules/am/InvertedIndexAccessMethod.java     |  24 +-
 ...oveFreeVariableOperatorOutOfSubplanRule.java |  30 +
 ...ineSubplanInputForNestedTupleSourceRule.java | 612 +++++++++++++++++++
 .../LangExpressionToPlanTranslator.java         |  43 +-
 .../queries/udfs/query-ASTERIXDB-1017-2.aql     |  63 ++
 .../udfs/query-ASTERIXDB-1017-recursive-2.aql   |  66 ++
 .../udfs/query-ASTERIXDB-1017-recursive.aql     |  66 ++
 .../queries/udfs/query-ASTERIXDB-1017.aql       |  69 +++
 .../queries/udfs/query-ASTERIXDB-1018.aql       |  63 ++
 .../queries/udfs/query-ASTERIXDB-1019.aql       |  75 +++
 .../queries/udfs/query-ASTERIXDB-1020.aql       |  61 ++
 .../queries/udfs/query-ASTERIXDB-1029.aql       |  66 ++
 .../queries/udfs/query-ASTERIXDB-1029_2.aql     |  66 ++
 .../queries/udfs/query-ASTERIXDB-1030_1034.aql  |  46 ++
 .../udfs/query-ASTERIXDB-1030_1034_2.aql        |  46 ++
 .../results/udfs/query-ASTERIXDB-1017-2.plan    |  69 +++
 .../udfs/query-ASTERIXDB-1017-recursive-2.plan  |  69 +++
 .../udfs/query-ASTERIXDB-1017-recursive.plan    |  76 +++
 .../results/udfs/query-ASTERIXDB-1017.plan      |  67 ++
 .../results/udfs/query-ASTERIXDB-1018.plan      |  78 +++
 .../results/udfs/query-ASTERIXDB-1019.plan      |  86 +++
 .../results/udfs/query-ASTERIXDB-1020.plan      |  46 ++
 .../results/udfs/query-ASTERIXDB-1029.plan      |  80 +++
 .../results/udfs/query-ASTERIXDB-1029_2.plan    |  80 +++
 .../results/udfs/query-ASTERIXDB-1030_1034.plan |  31 +
 .../udfs/query-ASTERIXDB-1030_1034_2.plan       |  31 +
 .../queries_sqlpp/dapd/q1/q1.3.query.sqlpp      |   2 +-
 .../results_parser_sqlpp/dapd/q1/q1.3.ast       |   7 +
 37 files changed, 2143 insertions(+), 765 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalExpressionDeepCopyVisitor.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalExpressionDeepCopyVisitor.java b/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalExpressionDeepCopyVisitor.java
deleted file mode 100644
index 47066d2..0000000
--- a/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalExpressionDeepCopyVisitor.java
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-package org.apache.asterix.algebra.base;
-
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-
-import org.apache.commons.lang3.mutable.Mutable;
-import org.apache.commons.lang3.mutable.MutableObject;
-
-import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
-import org.apache.hyracks.algebricks.core.algebra.base.Counter;
-import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.expressions.AbstractFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.AggregateFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.IExpressionAnnotation;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ScalarFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.StatefulFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.UnnestingFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.VariableReferenceExpression;
-import org.apache.hyracks.algebricks.core.algebra.visitors.ILogicalExpressionVisitor;
-
-public class LogicalExpressionDeepCopyVisitor implements ILogicalExpressionVisitor<ILogicalExpression, Void> {
-    private final Counter counter;
-    private final Map<LogicalVariable, LogicalVariable> inVarMapping;
-    private final Map<LogicalVariable, LogicalVariable> outVarMapping;
-
-    public LogicalExpressionDeepCopyVisitor(Counter counter, Map<LogicalVariable, LogicalVariable> inVarMapping,
-            Map<LogicalVariable, LogicalVariable> variableMapping) {
-        this.counter = counter;
-        this.inVarMapping = inVarMapping;
-        this.outVarMapping = variableMapping;
-    }
-
-    public ILogicalExpression deepCopy(ILogicalExpression expr) throws AlgebricksException {
-        return expr.accept(this, null);
-    }
-
-    private void deepCopyAnnotations(AbstractFunctionCallExpression src, AbstractFunctionCallExpression dest) {
-        Map<Object, IExpressionAnnotation> srcAnnotations = src.getAnnotations();
-        Map<Object, IExpressionAnnotation> destAnnotations = dest.getAnnotations();
-        for (Object k : srcAnnotations.keySet()) {
-            IExpressionAnnotation annotation = srcAnnotations.get(k).copy();
-            destAnnotations.put(k, annotation);
-        }
-    }
-
-    private void deepCopyOpaqueParameters(AbstractFunctionCallExpression src, AbstractFunctionCallExpression dest) {
-        Object[] srcOpaqueParameters = src.getOpaqueParameters();
-        Object[] newOpaqueParameters = null;
-        if (srcOpaqueParameters != null) {
-            newOpaqueParameters = new Object[srcOpaqueParameters.length];
-            for (int i = 0; i < srcOpaqueParameters.length; i++) {
-                newOpaqueParameters[i] = srcOpaqueParameters[i];
-            }
-        }
-        dest.setOpaqueParameters(newOpaqueParameters);
-    }
-
-    public MutableObject<ILogicalExpression> deepCopyExpressionReference(Mutable<ILogicalExpression> exprRef)
-            throws AlgebricksException {
-        return new MutableObject<ILogicalExpression>(deepCopy(exprRef.getValue()));
-    }
-
-    // TODO return List<...>
-    public ArrayList<Mutable<ILogicalExpression>> deepCopyExpressionReferenceList(
-            List<Mutable<ILogicalExpression>> list) throws AlgebricksException {
-        ArrayList<Mutable<ILogicalExpression>> listCopy = new ArrayList<Mutable<ILogicalExpression>>(list.size());
-        for (Mutable<ILogicalExpression> exprRef : list) {
-            listCopy.add(deepCopyExpressionReference(exprRef));
-        }
-        return listCopy;
-    }
-
-    @Override
-    public ILogicalExpression visitAggregateFunctionCallExpression(AggregateFunctionCallExpression expr, Void arg)
-            throws AlgebricksException {
-        AggregateFunctionCallExpression exprCopy = new AggregateFunctionCallExpression(expr.getFunctionInfo(),
-                expr.isTwoStep(), deepCopyExpressionReferenceList(expr.getArguments()));
-        deepCopyAnnotations(expr, exprCopy);
-        deepCopyOpaqueParameters(expr, exprCopy);
-        return exprCopy;
-    }
-
-    @Override
-    public ILogicalExpression visitConstantExpression(ConstantExpression expr, Void arg) throws AlgebricksException {
-        return new ConstantExpression(expr.getValue());
-    }
-
-    @Override
-    public ILogicalExpression visitScalarFunctionCallExpression(ScalarFunctionCallExpression expr, Void arg)
-            throws AlgebricksException {
-        ScalarFunctionCallExpression exprCopy = new ScalarFunctionCallExpression(expr.getFunctionInfo(),
-                deepCopyExpressionReferenceList(expr.getArguments()));
-        deepCopyAnnotations(expr, exprCopy);
-        deepCopyOpaqueParameters(expr, exprCopy);
-        return exprCopy;
-
-    }
-
-    @Override
-    public ILogicalExpression visitStatefulFunctionCallExpression(StatefulFunctionCallExpression expr, Void arg)
-            throws AlgebricksException {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalExpression visitUnnestingFunctionCallExpression(UnnestingFunctionCallExpression expr, Void arg)
-            throws AlgebricksException {
-        UnnestingFunctionCallExpression exprCopy = new UnnestingFunctionCallExpression(expr.getFunctionInfo(),
-                deepCopyExpressionReferenceList(expr.getArguments()));
-        deepCopyAnnotations(expr, exprCopy);
-        deepCopyOpaqueParameters(expr, exprCopy);
-        return exprCopy;
-    }
-
-    @Override
-    public ILogicalExpression visitVariableReferenceExpression(VariableReferenceExpression expr, Void arg)
-            throws AlgebricksException {
-        LogicalVariable var = expr.getVariableReference();
-        LogicalVariable givenVarReplacement = inVarMapping.get(var);
-        if (givenVarReplacement != null) {
-            outVarMapping.put(var, givenVarReplacement);
-            return new VariableReferenceExpression(givenVarReplacement);
-        }
-        LogicalVariable varCopy = outVarMapping.get(var);
-        if (varCopy == null) {
-            counter.inc();
-            varCopy = new LogicalVariable(counter.get());
-            outVarMapping.put(var, varCopy);
-        }
-        return new VariableReferenceExpression(varCopy);
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalOperatorDeepCopyVisitor.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalOperatorDeepCopyVisitor.java b/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalOperatorDeepCopyVisitor.java
deleted file mode 100644
index 7992936..0000000
--- a/asterix-algebra/src/main/java/org/apache/asterix/algebra/base/LogicalOperatorDeepCopyVisitor.java
+++ /dev/null
@@ -1,490 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-package org.apache.asterix.algebra.base;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.List;
-import java.util.Map;
-
-import org.apache.commons.lang3.mutable.Mutable;
-import org.apache.commons.lang3.mutable.MutableObject;
-import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
-import org.apache.hyracks.algebricks.common.utils.Pair;
-import org.apache.hyracks.algebricks.core.algebra.base.Counter;
-import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
-import org.apache.hyracks.algebricks.core.algebra.base.ILogicalOperator;
-import org.apache.hyracks.algebricks.core.algebra.base.ILogicalPlan;
-import org.apache.hyracks.algebricks.core.algebra.base.IOptimizationContext;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AggregateOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AssignOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.DataSourceScanOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.DistinctOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.DistributeResultOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.EmptyTupleSourceOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ExchangeOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ExtensionOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ExternalDataLookupOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.GroupByOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.IndexInsertDeleteOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.InnerJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.InsertDeleteOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.LeftOuterJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.LimitOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.MaterializeOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.NestedTupleSourceOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.OrderOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.OrderOperator.IOrder;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.OuterUnnestOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.PartitioningSplitOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ProjectOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ReplicateOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.RunningAggregateOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ScriptOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SelectOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SinkOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SubplanOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.TokenizeOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnionAllOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnnestMapOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnnestOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.WriteOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.WriteResultOperator;
-import org.apache.hyracks.algebricks.core.algebra.plan.ALogicalPlanImpl;
-import org.apache.hyracks.algebricks.core.algebra.properties.FunctionalDependency;
-import org.apache.hyracks.algebricks.core.algebra.visitors.ILogicalOperatorVisitor;
-
-public class LogicalOperatorDeepCopyVisitor implements ILogicalOperatorVisitor<ILogicalOperator, ILogicalOperator> {
-    private final Counter counter;
-    private final LogicalExpressionDeepCopyVisitor exprDeepCopyVisitor;
-
-    // Key: Variable in the original plan. Value: New variable replacing the
-    // original one in the copied plan.
-    private final Map<LogicalVariable, LogicalVariable> outVarMapping = new HashMap<LogicalVariable, LogicalVariable>();
-
-    // Key: Variable in the original plan. Value: Variable with which to replace
-    // original variable in the plan copy.
-    private final Map<LogicalVariable, LogicalVariable> inVarMapping;
-
-    public LogicalOperatorDeepCopyVisitor(Counter counter) {
-        this.counter = counter;
-        this.inVarMapping = Collections.emptyMap();
-        exprDeepCopyVisitor = new LogicalExpressionDeepCopyVisitor(counter, inVarMapping, outVarMapping);
-    }
-
-    /**
-     * @param counter
-     *            Starting variable counter.
-     * @param inVarMapping
-     *            Variable mapping keyed by variables in the original plan.
-     *            Those variables are replaced by their corresponding value in
-     *            the map in the copied plan.
-     */
-    public LogicalOperatorDeepCopyVisitor(Counter counter, Map<LogicalVariable, LogicalVariable> inVarMapping) {
-        this.counter = counter;
-        this.inVarMapping = inVarMapping;
-        exprDeepCopyVisitor = new LogicalExpressionDeepCopyVisitor(counter, inVarMapping, outVarMapping);
-    }
-
-    private void copyAnnotations(ILogicalOperator src, ILogicalOperator dest) {
-        dest.getAnnotations().putAll(src.getAnnotations());
-    }
-
-    public ILogicalOperator deepCopy(ILogicalOperator op, ILogicalOperator arg) throws AlgebricksException {
-        return op.accept(this, arg);
-    }
-
-    private void deepCopyInputs(ILogicalOperator src, ILogicalOperator dest, ILogicalOperator arg)
-            throws AlgebricksException {
-        List<Mutable<ILogicalOperator>> inputs = src.getInputs();
-        List<Mutable<ILogicalOperator>> inputsCopy = dest.getInputs();
-        for (Mutable<ILogicalOperator> input : inputs) {
-            inputsCopy.add(deepCopyOperatorReference(input, arg));
-        }
-    }
-
-    private Mutable<ILogicalOperator> deepCopyOperatorReference(Mutable<ILogicalOperator> opRef, ILogicalOperator arg)
-            throws AlgebricksException {
-        return new MutableObject<ILogicalOperator>(deepCopy(opRef.getValue(), arg));
-    }
-
-    private List<Mutable<ILogicalOperator>> deepCopyOperatorReferenceList(List<Mutable<ILogicalOperator>> list,
-            ILogicalOperator arg) throws AlgebricksException {
-        List<Mutable<ILogicalOperator>> listCopy = new ArrayList<Mutable<ILogicalOperator>>(list.size());
-        for (Mutable<ILogicalOperator> opRef : list) {
-            listCopy.add(deepCopyOperatorReference(opRef, arg));
-        }
-        return listCopy;
-    }
-
-    private IOrder deepCopyOrder(IOrder order) {
-        switch (order.getKind()) {
-            case ASC:
-            case DESC:
-                return order;
-            case FUNCTIONCALL:
-            default:
-                throw new UnsupportedOperationException();
-        }
-    }
-
-    private List<Pair<IOrder, Mutable<ILogicalExpression>>> deepCopyOrderExpressionReferencePairList(
-            List<Pair<IOrder, Mutable<ILogicalExpression>>> list) throws AlgebricksException {
-        ArrayList<Pair<IOrder, Mutable<ILogicalExpression>>> listCopy = new ArrayList<Pair<IOrder, Mutable<ILogicalExpression>>>(
-                list.size());
-        for (Pair<IOrder, Mutable<ILogicalExpression>> pair : list) {
-            listCopy.add(new Pair<OrderOperator.IOrder, Mutable<ILogicalExpression>>(deepCopyOrder(pair.first),
-                    exprDeepCopyVisitor.deepCopyExpressionReference(pair.second)));
-        }
-        return listCopy;
-    }
-
-    private ILogicalPlan deepCopyPlan(ILogicalPlan plan, ILogicalOperator arg) throws AlgebricksException {
-        List<Mutable<ILogicalOperator>> rootsCopy = deepCopyOperatorReferenceList(plan.getRoots(), arg);
-        ILogicalPlan planCopy = new ALogicalPlanImpl(rootsCopy);
-        return planCopy;
-    }
-
-    private List<ILogicalPlan> deepCopyPlanList(List<ILogicalPlan> list, List<ILogicalPlan> listCopy,
-            ILogicalOperator arg) throws AlgebricksException {
-        for (ILogicalPlan plan : list) {
-            listCopy.add(deepCopyPlan(plan, arg));
-        }
-        return listCopy;
-    }
-
-    private LogicalVariable deepCopyVariable(LogicalVariable var) {
-        if (var == null) {
-            return null;
-        }
-        LogicalVariable givenVarReplacement = inVarMapping.get(var);
-        if (givenVarReplacement != null) {
-            outVarMapping.put(var, givenVarReplacement);
-            return givenVarReplacement;
-        }
-        LogicalVariable varCopy = outVarMapping.get(var);
-        if (varCopy == null) {
-            counter.inc();
-            varCopy = new LogicalVariable(counter.get());
-            outVarMapping.put(var, varCopy);
-        }
-        return varCopy;
-    }
-
-    private List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> deepCopyVariableExpressionReferencePairList(
-            List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> list) throws AlgebricksException {
-        List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> listCopy = new ArrayList<Pair<LogicalVariable, Mutable<ILogicalExpression>>>(
-                list.size());
-        for (Pair<LogicalVariable, Mutable<ILogicalExpression>> pair : list) {
-            listCopy.add(new Pair<LogicalVariable, Mutable<ILogicalExpression>>(deepCopyVariable(pair.first),
-                    exprDeepCopyVisitor.deepCopyExpressionReference(pair.second)));
-        }
-        return listCopy;
-    }
-
-    // TODO return List<...>
-    private ArrayList<LogicalVariable> deepCopyVariableList(List<LogicalVariable> list) {
-        ArrayList<LogicalVariable> listCopy = new ArrayList<LogicalVariable>(list.size());
-        for (LogicalVariable var : list) {
-            listCopy.add(deepCopyVariable(var));
-        }
-        return listCopy;
-    }
-
-    public void reset() {
-        outVarMapping.clear();
-    }
-
-    public void updatePrimaryKeys(IOptimizationContext context) {
-        for (Map.Entry<LogicalVariable, LogicalVariable> entry : outVarMapping.entrySet()) {
-            List<LogicalVariable> primaryKey = context.findPrimaryKey(entry.getKey());
-            if (primaryKey != null) {
-                List<LogicalVariable> head = new ArrayList<LogicalVariable>();
-                for (LogicalVariable variable : primaryKey) {
-                    head.add(outVarMapping.get(variable));
-                }
-                List<LogicalVariable> tail = new ArrayList<LogicalVariable>(1);
-                tail.add(entry.getValue());
-                context.addPrimaryKey(new FunctionalDependency(head, tail));
-            }
-        }
-    }
-
-    public LogicalVariable varCopy(LogicalVariable var) throws AlgebricksException {
-        return outVarMapping.get(var);
-    }
-
-    @Override
-    public ILogicalOperator visitAggregateOperator(AggregateOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        AggregateOperator opCopy = new AggregateOperator(deepCopyVariableList(op.getVariables()),
-                exprDeepCopyVisitor.deepCopyExpressionReferenceList(op.getExpressions()));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitAssignOperator(AssignOperator op, ILogicalOperator arg) throws AlgebricksException {
-        AssignOperator opCopy = new AssignOperator(deepCopyVariableList(op.getVariables()),
-                exprDeepCopyVisitor.deepCopyExpressionReferenceList(op.getExpressions()));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitDataScanOperator(DataSourceScanOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        DataSourceScanOperator opCopy = new DataSourceScanOperator(deepCopyVariableList(op.getVariables()),
-                op.getDataSource());
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitDistinctOperator(DistinctOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitEmptyTupleSourceOperator(EmptyTupleSourceOperator op, ILogicalOperator arg) {
-        EmptyTupleSourceOperator opCopy = new EmptyTupleSourceOperator();
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitExchangeOperator(ExchangeOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitGroupByOperator(GroupByOperator op, ILogicalOperator arg) throws AlgebricksException {
-        List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> groupByListCopy = deepCopyVariableExpressionReferencePairList(
-                op.getGroupByList());
-        List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> decorListCopy = deepCopyVariableExpressionReferencePairList(
-                op.getDecorList());
-        List<ILogicalPlan> nestedPlansCopy = new ArrayList<ILogicalPlan>();
-
-        GroupByOperator opCopy = new GroupByOperator(groupByListCopy, decorListCopy, nestedPlansCopy);
-        deepCopyPlanList(op.getNestedPlans(), nestedPlansCopy, opCopy);
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitInnerJoinOperator(InnerJoinOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        InnerJoinOperator opCopy = new InnerJoinOperator(
-                exprDeepCopyVisitor.deepCopyExpressionReference(op.getCondition()),
-                deepCopyOperatorReference(op.getInputs().get(0), null),
-                deepCopyOperatorReference(op.getInputs().get(1), null));
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitLeftOuterJoinOperator(LeftOuterJoinOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitLimitOperator(LimitOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitNestedTupleSourceOperator(NestedTupleSourceOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        NestedTupleSourceOperator opCopy = new NestedTupleSourceOperator(new MutableObject<ILogicalOperator>(arg));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitOrderOperator(OrderOperator op, ILogicalOperator arg) throws AlgebricksException {
-        OrderOperator opCopy = new OrderOperator(deepCopyOrderExpressionReferencePairList(op.getOrderExpressions()));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitPartitioningSplitOperator(PartitioningSplitOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitProjectOperator(ProjectOperator op, ILogicalOperator arg) throws AlgebricksException {
-        ProjectOperator opCopy = new ProjectOperator(deepCopyVariableList(op.getVariables()));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitReplicateOperator(ReplicateOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitMaterializeOperator(MaterializeOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitRunningAggregateOperator(RunningAggregateOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitScriptOperator(ScriptOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitSelectOperator(SelectOperator op, ILogicalOperator arg) throws AlgebricksException {
-        SelectOperator opCopy = new SelectOperator(exprDeepCopyVisitor.deepCopyExpressionReference(op.getCondition()),
-                op.getRetainNull(), deepCopyVariable(op.getNullPlaceholderVariable()));
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitSubplanOperator(SubplanOperator op, ILogicalOperator arg) throws AlgebricksException {
-        List<ILogicalPlan> nestedPlansCopy = new ArrayList<ILogicalPlan>();
-
-        SubplanOperator opCopy = new SubplanOperator(nestedPlansCopy);
-        deepCopyPlanList(op.getNestedPlans(), nestedPlansCopy, opCopy);
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitUnionOperator(UnionAllOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitUnnestMapOperator(UnnestMapOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        UnnestMapOperator opCopy = new UnnestMapOperator(deepCopyVariableList(op.getVariables()),
-                exprDeepCopyVisitor.deepCopyExpressionReference(op.getExpressionRef()), op.getVariableTypes(),
-                op.propagatesInput());
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitUnnestOperator(UnnestOperator op, ILogicalOperator arg) throws AlgebricksException {
-        UnnestOperator opCopy = new UnnestOperator(deepCopyVariable(op.getVariable()),
-                exprDeepCopyVisitor.deepCopyExpressionReference(op.getExpressionRef()),
-                deepCopyVariable(op.getPositionalVariable()), op.getPositionalVariableType(), op.getPositionWriter());
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-    @Override
-    public ILogicalOperator visitWriteOperator(WriteOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitDistributeResultOperator(DistributeResultOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitWriteResultOperator(WriteResultOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitInsertDeleteOperator(InsertDeleteOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitIndexInsertDeleteOperator(IndexInsertDeleteOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitTokenizeOperator(TokenizeOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitSinkOperator(SinkOperator op, ILogicalOperator arg) {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitExtensionOperator(ExtensionOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        throw new UnsupportedOperationException();
-    }
-
-    public Map<LogicalVariable, LogicalVariable> getVariableMapping() {
-        return outVarMapping;
-    }
-
-    @Override
-    public ILogicalOperator visitExternalDataLookupOperator(ExternalDataLookupOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        throw new UnsupportedOperationException();
-    }
-
-    @Override
-    public ILogicalOperator visitOuterUnnestOperator(OuterUnnestOperator op, ILogicalOperator arg)
-            throws AlgebricksException {
-        OuterUnnestOperator opCopy = new OuterUnnestOperator(deepCopyVariable(op.getVariable()),
-                exprDeepCopyVisitor.deepCopyExpressionReference(op.getExpressionRef()),
-                deepCopyVariable(op.getPositionalVariable()), op.getPositionalVariableType(), op.getPositionWriter());
-        deepCopyInputs(op, opCopy, arg);
-        copyAnnotations(op, opCopy);
-        opCopy.setExecutionMode(op.getExecutionMode());
-        return opCopy;
-    }
-
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/base/RuleCollections.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/base/RuleCollections.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/base/RuleCollections.java
index 2d2678c..260fb3c 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/base/RuleCollections.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/base/RuleCollections.java
@@ -26,7 +26,6 @@ import org.apache.asterix.optimizer.rules.AddEquivalenceClassForRecordConstructo
 import org.apache.asterix.optimizer.rules.AsterixExtractFunctionsFromJoinConditionRule;
 import org.apache.asterix.optimizer.rules.AsterixInlineVariablesRule;
 import org.apache.asterix.optimizer.rules.AsterixIntroduceGroupByCombinerRule;
-import org.apache.asterix.optimizer.rules.AsterixMoveFreeVariableOperatorOutOfSubplanRule;
 import org.apache.asterix.optimizer.rules.ByNameToByIndexFieldAccessRule;
 import org.apache.asterix.optimizer.rules.CancelUnnestWithNestedListifyRule;
 import org.apache.asterix.optimizer.rules.CheckFilterExpressionTypeRule;
@@ -72,6 +71,8 @@ import org.apache.asterix.optimizer.rules.UnnestToDataScanRule;
 import org.apache.asterix.optimizer.rules.am.IntroduceJoinAccessMethodRule;
 import org.apache.asterix.optimizer.rules.am.IntroduceLSMComponentFilterRule;
 import org.apache.asterix.optimizer.rules.am.IntroduceSelectAccessMethodRule;
+import org.apache.asterix.optimizer.rules.subplan.AsterixMoveFreeVariableOperatorOutOfSubplanRule;
+import org.apache.asterix.optimizer.rules.subplan.InlineSubplanInputForNestedTupleSourceRule;
 import org.apache.asterix.optimizer.rules.temporal.TranslateIntervalExpressionRule;
 import org.apache.hyracks.algebricks.core.rewriter.base.HeuristicOptimizer;
 import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
@@ -82,8 +83,6 @@ import org.apache.hyracks.algebricks.rewriter.rules.ConsolidateAssignsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ConsolidateSelectsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.CopyLimitDownRule;
 import org.apache.hyracks.algebricks.rewriter.rules.EliminateGroupByEmptyKeyRule;
-import org.apache.hyracks.algebricks.rewriter.rules.EliminateSubplanRule;
-import org.apache.hyracks.algebricks.rewriter.rules.EliminateSubplanWithInputCardinalityOneRule;
 import org.apache.hyracks.algebricks.rewriter.rules.EnforceOrderByAfterSubplan;
 import org.apache.hyracks.algebricks.rewriter.rules.EnforceStructuralPropertiesRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ExtractCommonExpressionsRule;
@@ -93,14 +92,11 @@ import org.apache.hyracks.algebricks.rewriter.rules.FactorRedundantGroupAndDecor
 import org.apache.hyracks.algebricks.rewriter.rules.InferTypesRule;
 import org.apache.hyracks.algebricks.rewriter.rules.InlineAssignIntoAggregateRule;
 import org.apache.hyracks.algebricks.rewriter.rules.InlineSingleReferenceVariablesRule;
-import org.apache.hyracks.algebricks.rewriter.rules.InsertOuterJoinRule;
 import org.apache.hyracks.algebricks.rewriter.rules.InsertProjectBeforeUnionRule;
 import org.apache.hyracks.algebricks.rewriter.rules.IntroJoinInsideSubplanRule;
 import org.apache.hyracks.algebricks.rewriter.rules.IntroduceAggregateCombinerRule;
-import org.apache.hyracks.algebricks.rewriter.rules.IntroduceGroupByForSubplanRule;
 import org.apache.hyracks.algebricks.rewriter.rules.IntroduceProjectsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.IsolateHyracksOperatorsRule;
-import org.apache.hyracks.algebricks.rewriter.rules.NestedSubplanToJoinRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PullSelectOutOfEqJoin;
 import org.apache.hyracks.algebricks.rewriter.rules.PushAssignBelowUnionAllRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushGroupByIntoSortRule;
@@ -110,7 +106,6 @@ import org.apache.hyracks.algebricks.rewriter.rules.PushProjectDownRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushSelectDownRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushSelectIntoJoinRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushSortDownRule;
-import org.apache.hyracks.algebricks.rewriter.rules.PushSubplanIntoGroupByRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushSubplanWithAggregateDownThroughProductRule;
 import org.apache.hyracks.algebricks.rewriter.rules.PushUnnestDownThroughUnionRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ReinferAllTypesRule;
@@ -121,7 +116,13 @@ import org.apache.hyracks.algebricks.rewriter.rules.RemoveUnusedAssignAndAggrega
 import org.apache.hyracks.algebricks.rewriter.rules.SetAlgebricksPhysicalOperatorsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.SetExecutionModeRule;
 import org.apache.hyracks.algebricks.rewriter.rules.SimpleUnnestToProductRule;
-import org.apache.hyracks.algebricks.rewriter.rules.SubplanOutOfGroupRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.EliminateSubplanRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.EliminateSubplanWithInputCardinalityOneRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.IntroduceGroupByForSubplanRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.IntroduceLeftOuterJoinForSubplanRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.NestedSubplanToJoinRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.PushSubplanIntoGroupByRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.SubplanOutOfGroupRule;
 
 public final class RuleCollections {
 
@@ -191,7 +192,7 @@ public final class RuleCollections {
         condPushDownAndJoinInference.add(new PushSubplanWithAggregateDownThroughProductRule());
         condPushDownAndJoinInference.add(new IntroduceGroupByForSubplanRule());
         condPushDownAndJoinInference.add(new SubplanOutOfGroupRule());
-        condPushDownAndJoinInference.add(new InsertOuterJoinRule());
+        condPushDownAndJoinInference.add(new IntroduceLeftOuterJoinForSubplanRule());
         condPushDownAndJoinInference.add(new AsterixExtractFunctionsFromJoinConditionRule());
 
         condPushDownAndJoinInference.add(new RemoveRedundantVariablesRule());
@@ -222,8 +223,10 @@ public final class RuleCollections {
         fieldLoads.add(new AsterixInlineVariablesRule());
         fieldLoads.add(new RemoveUnusedAssignAndAggregateRule());
         fieldLoads.add(new ConstantFoldingRule());
+        fieldLoads.add(new RemoveRedundantSelectRule());
         fieldLoads.add(new FeedScanCollectionToUnnest());
         fieldLoads.add(new ComplexJoinInferenceRule());
+        fieldLoads.add(new InlineSubplanInputForNestedTupleSourceRule());
         return fieldLoads;
     }
 
@@ -244,12 +247,10 @@ public final class RuleCollections {
         consolidation.add(new CountVarToCountOneRule());
         consolidation.add(new RemoveUnusedAssignAndAggregateRule());
         consolidation.add(new RemoveRedundantGroupByDecorVars());
-        consolidation.add(new NestedSubplanToJoinRule());
         //unionRule => PushUnnestDownUnion => RemoveRedundantListifyRule cause these rules are correlated
         consolidation.add(new IntroduceUnionRule());
         consolidation.add(new PushUnnestDownThroughUnionRule());
         consolidation.add(new RemoveRedundantListifyRule());
-
         return consolidation;
     }
 

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
deleted file mode 100644
index 351ca63..0000000
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-package org.apache.asterix.optimizer.rules;
-
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.rewriter.rules.MoveFreeVariableOperatorOutOfSubplanRule;
-
-public class AsterixMoveFreeVariableOperatorOutOfSubplanRule extends MoveFreeVariableOperatorOutOfSubplanRule {
-
-    @Override
-    protected boolean movableOperator(LogicalOperatorTag operatorTag) {
-        return (operatorTag == LogicalOperatorTag.ASSIGN);
-    }
-}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/FuzzyJoinRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/FuzzyJoinRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/FuzzyJoinRule.java
index 6faf77c..1741008 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/FuzzyJoinRule.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/FuzzyJoinRule.java
@@ -24,9 +24,6 @@ import java.util.HashSet;
 import java.util.List;
 import java.util.Locale;
 
-import org.apache.commons.lang3.mutable.Mutable;
-import org.apache.commons.lang3.mutable.MutableObject;
-import org.apache.asterix.algebra.base.LogicalOperatorDeepCopyVisitor;
 import org.apache.asterix.aqlplus.parser.AQLPlusParser;
 import org.apache.asterix.aqlplus.parser.ParseException;
 import org.apache.asterix.common.exceptions.AsterixException;
@@ -38,6 +35,8 @@ import org.apache.asterix.om.types.IAType;
 import org.apache.asterix.om.types.TypeHelper;
 import org.apache.asterix.optimizer.base.FuzzyUtils;
 import org.apache.asterix.translator.AqlPlusExpressionToPlanTranslator;
+import org.apache.commons.lang3.mutable.Mutable;
+import org.apache.commons.lang3.mutable.MutableObject;
 import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
 import org.apache.hyracks.algebricks.core.algebra.base.Counter;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
@@ -57,6 +56,7 @@ import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractBina
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.LeftOuterJoinOperator;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.SelectOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.LogicalOperatorDeepCopyWithNewVariablesVisitor;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.VariableUtilities;
 import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
 import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
@@ -64,6 +64,7 @@ import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
 public class FuzzyJoinRule implements IAlgebraicRewriteRule {
 
     private static HashSet<FunctionIdentifier> simFuncs = new HashSet<FunctionIdentifier>();
+
     static {
         simFuncs.add(AsterixBuiltinFunctions.SIMILARITY_JACCARD_CHECK);
     }
@@ -72,68 +73,45 @@ public class FuzzyJoinRule implements IAlgebraicRewriteRule {
             //
             // -- - Stage 3 - --
             //
-            + "((#RIGHT), "
-            + "  (join((#LEFT), "
+            + "((#RIGHT), " + "  (join((#LEFT), "
             //
             // -- -- - Stage 2 - --
             //
-            + "    ("
-            + "    join( "
-            + "      ( "
-            + "      #LEFT_1 "
-            + "      let $tokensUnrankedLeft := %s($$LEFT_1) "
-            + "      let $lenLeft := len($tokensUnrankedLeft) "
-            + "      let $tokensLeft := "
-            + "        for $token in $tokensUnrankedLeft "
-            + "        for $tokenRanked at $i in "
+            + "    (" + "    join( " + "      ( " + "      #LEFT_1 " + "      let $tokensUnrankedLeft := %s($$LEFT_1) "
+            + "      let $lenLeft := len($tokensUnrankedLeft) " + "      let $tokensLeft := "
+            + "        for $token in $tokensUnrankedLeft " + "        for $tokenRanked at $i in "
             //
             // -- -- -- - Stage 1 - --
             //
             // + "          #LEFT_2 "
             // + "          let $id := $$LEFTPK_2 "
             // + "          for $token in %s($$LEFT_2) "
-            + "          #RIGHT_2 "
-            + "          let $id := $$RIGHTPK_2 "
-            + "          for $token in %s($$RIGHT_2) "
-            + "          /*+ hash */ "
-            + "          group by $tokenGroupped := $token with $id "
-            + "          /*+ inmem 34 198608 */ "
-            + "          order by count($id), $tokenGroupped "
+            + "          #RIGHT_2 " + "          let $id := $$RIGHTPK_2 " + "          for $token in %s($$RIGHT_2) "
+            + "          /*+ hash */ " + "          group by $tokenGroupped := $token with $id "
+            + "          /*+ inmem 34 198608 */ " + "          order by count($id), $tokenGroupped "
             + "          return $tokenGroupped "
             //
             // -- -- -- -
             //
-            + "        where $token = /*+ bcast */ $tokenRanked "
-            + "        order by $i "
-            + "        return $i "
+            + "        where $token = /*+ bcast */ $tokenRanked " + "        order by $i " + "        return $i "
             + "      for $prefixTokenLeft in subset-collection($tokensLeft, 0, prefix-len-%s(len($tokensLeft), %ff)) "
-            + "      ),( "
-            + "      #RIGHT_1 "
-            + "      let $tokensUnrankedRight := %s($$RIGHT_1) "
-            + "      let $lenRight := len($tokensUnrankedRight) "
-            + "      let $tokensRight := "
-            + "        for $token in $tokensUnrankedRight "
-            + "        for $tokenRanked at $i in "
+            + "      ),( " + "      #RIGHT_1 " + "      let $tokensUnrankedRight := %s($$RIGHT_1) "
+            + "      let $lenRight := len($tokensUnrankedRight) " + "      let $tokensRight := "
+            + "        for $token in $tokensUnrankedRight " + "        for $tokenRanked at $i in "
             //
             // -- -- -- - Stage 1 - --
             //
             // + "          #LEFT_3 "
             // + "          let $id := $$LEFTPK_3 "
             // + "          for $token in %s($$LEFT_3) "
-            + "          #RIGHT_3 "
-            + "          let $id := $$RIGHTPK_3 "
-            + "          for $token in %s($$RIGHT_3) "
-            + "          /*+ hash */ "
-            + "          group by $tokenGroupped := $token with $id "
-            + "          /*+ inmem 34 198608 */ "
-            + "          order by count($id), $tokenGroupped "
+            + "          #RIGHT_3 " + "          let $id := $$RIGHTPK_3 " + "          for $token in %s($$RIGHT_3) "
+            + "          /*+ hash */ " + "          group by $tokenGroupped := $token with $id "
+            + "          /*+ inmem 34 198608 */ " + "          order by count($id), $tokenGroupped "
             + "          return $tokenGroupped "
             //
             // -- -- -- -
             //
-            + "        where $token = /*+ bcast */ $tokenRanked "
-            + "        order by $i "
-            + "        return $i "
+            + "        where $token = /*+ bcast */ $tokenRanked " + "        order by $i " + "        return $i "
             + "      for $prefixTokenRight in subset-collection($tokensRight, 0, prefix-len-%s(len($tokensRight), %ff)) "
             + "      ), $prefixTokenLeft = $prefixTokenRight) "
             + "    let $sim := similarity-%s-prefix($lenLeft, $tokensLeft, $lenRight, $tokensRight, $prefixTokenLeft, %ff) "
@@ -285,8 +263,10 @@ public class FuzzyJoinRule implements IAlgebraicRewriteRule {
         // under the same transaction id as the "outer" compilation.
         AqlPlusExpressionToPlanTranslator translator = new AqlPlusExpressionToPlanTranslator(
                 metadataProvider.getJobId(), metadataProvider, counter, null, null);
+        context.setVarCounter(counter.get());
 
-        LogicalOperatorDeepCopyVisitor deepCopyVisitor = new LogicalOperatorDeepCopyVisitor(counter);
+        LogicalOperatorDeepCopyWithNewVariablesVisitor deepCopyVisitor = new LogicalOperatorDeepCopyWithNewVariablesVisitor(
+                context);
 
         translator.addOperatorToMetaScope(new Identifier("#LEFT"), leftInputOp);
         translator.addVariableToMetaScope(new Identifier("$$LEFT"), leftInputVar);
@@ -401,7 +381,8 @@ public class FuzzyJoinRule implements IAlgebraicRewriteRule {
     }
 
     @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
+    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
+            throws AlgebricksException {
         return false;
     }
 }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/PushGroupByThroughProduct.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/PushGroupByThroughProduct.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/PushGroupByThroughProduct.java
index b9db064..903f49e 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/PushGroupByThroughProduct.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/PushGroupByThroughProduct.java
@@ -25,7 +25,6 @@ import java.util.List;
 import java.util.Set;
 
 import org.apache.commons.lang3.mutable.Mutable;
-
 import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
 import org.apache.hyracks.algebricks.common.utils.Pair;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
@@ -54,7 +53,8 @@ public class PushGroupByThroughProduct implements IAlgebraicRewriteRule {
     }
 
     @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
+    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
+            throws AlgebricksException {
         return false;
     }
 
@@ -110,16 +110,18 @@ public class PushGroupByThroughProduct implements IAlgebraicRewriteRule {
     private void push(Mutable<ILogicalOperator> opRefGby, Mutable<ILogicalOperator> opRefJoin, int branch,
             List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> decorToPush,
             List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> decorNotToPush, IOptimizationContext context)
-            throws AlgebricksException {
+                    throws AlgebricksException {
         GroupByOperator gby = (GroupByOperator) opRefGby.getValue();
         AbstractBinaryJoinOperator join = (AbstractBinaryJoinOperator) opRefJoin.getValue();
         gby.getDecorList().clear();
         gby.getDecorList().addAll(decorToPush);
         for (Pair<LogicalVariable, Mutable<ILogicalExpression>> p : decorNotToPush) {
             LogicalVariable v1 = p.first;
-            VariableReferenceExpression varRef = (VariableReferenceExpression) p.second.getValue();
-            LogicalVariable v2 = varRef.getVariableReference();
-            OperatorManipulationUtil.substituteVarRec(join, v2, v1, true, context);
+            if (v1 != null) {
+                VariableReferenceExpression varRef = (VariableReferenceExpression) p.second.getValue();
+                LogicalVariable v2 = varRef.getVariableReference();
+                OperatorManipulationUtil.substituteVarRec(join, v2, v1, true, context);
+            }
         }
         Mutable<ILogicalOperator> branchRef = join.getInputs().get(branch);
         ILogicalOperator opBranch = branchRef.getValue();

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/UnnestToDataScanRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/UnnestToDataScanRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/UnnestToDataScanRule.java
index 4ad5cec..dab6193 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/UnnestToDataScanRule.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/UnnestToDataScanRule.java
@@ -21,8 +21,6 @@ package org.apache.asterix.optimizer.rules;
 import java.util.ArrayList;
 import java.util.List;
 
-import org.apache.commons.lang3.mutable.Mutable;
-
 import org.apache.asterix.common.config.DatasetConfig.DatasetType;
 import org.apache.asterix.common.feeds.FeedActivity.FeedActivityDetails;
 import org.apache.asterix.common.feeds.api.IFeedLifecycleListener.ConnectionLocation;
@@ -43,6 +41,7 @@ import org.apache.asterix.om.types.ARecordType;
 import org.apache.asterix.om.types.ATypeTag;
 import org.apache.asterix.om.types.IAType;
 import org.apache.asterix.optimizer.rules.util.EquivalenceClassUtils;
+import org.apache.commons.lang3.mutable.Mutable;
 import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
 import org.apache.hyracks.algebricks.common.utils.Pair;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/AbstractIntroduceAccessMethodRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/AbstractIntroduceAccessMethodRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/AbstractIntroduceAccessMethodRule.java
index 3a86a6f..70b6770 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/AbstractIntroduceAccessMethodRule.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/AbstractIntroduceAccessMethodRule.java
@@ -798,4 +798,4 @@ public abstract class AbstractIntroduceAccessMethodRule implements IAlgebraicRew
         }
         return null;
     }
-}
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/IntroduceJoinAccessMethodRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/IntroduceJoinAccessMethodRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/IntroduceJoinAccessMethodRule.java
index dd30415..44314ff 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/IntroduceJoinAccessMethodRule.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/IntroduceJoinAccessMethodRule.java
@@ -241,8 +241,12 @@ public class IntroduceJoinAccessMethodRule extends AbstractIntroduceAccessMethod
             return false;
         }
         joinCond = (AbstractFunctionCallExpression) condExpr;
-        leftSubTree.initFromSubTree(join.getInputs().get(0));
-        rightSubTree.initFromSubTree(join.getInputs().get(1));
+        boolean leftSubTreeInitialized = leftSubTree.initFromSubTree(join.getInputs().get(0));
+        boolean rightSubTreeInitialized = rightSubTree.initFromSubTree(join.getInputs().get(1));
+        if (!leftSubTreeInitialized || !rightSubTreeInitialized) {
+            return false;
+        }
+
         // One of the subtrees must have a datasource scan.
         if (leftSubTree.hasDataSourceScan() || rightSubTree.hasDataSourceScan()) {
             return true;

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/InvertedIndexAccessMethod.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/InvertedIndexAccessMethod.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/InvertedIndexAccessMethod.java
index 9bc49f8..35b4075 100644
--- a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/InvertedIndexAccessMethod.java
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/am/InvertedIndexAccessMethod.java
@@ -24,7 +24,6 @@ import java.util.HashSet;
 import java.util.List;
 import java.util.Map;
 
-import org.apache.asterix.algebra.base.LogicalOperatorDeepCopyVisitor;
 import org.apache.asterix.common.annotations.SkipSecondaryIndexSearchExpressionAnnotation;
 import org.apache.asterix.common.config.DatasetConfig.IndexType;
 import org.apache.asterix.common.exceptions.AsterixException;
@@ -49,7 +48,6 @@ import org.apache.commons.lang3.mutable.Mutable;
 import org.apache.commons.lang3.mutable.MutableObject;
 import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
 import org.apache.hyracks.algebricks.common.utils.Triple;
-import org.apache.hyracks.algebricks.core.algebra.base.Counter;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalExpression;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalOperator;
 import org.apache.hyracks.algebricks.core.algebra.base.IOptimizationContext;
@@ -74,6 +72,7 @@ import org.apache.hyracks.algebricks.core.algebra.operators.logical.SelectOperat
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnionAllOperator;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnnestMapOperator;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnnestOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.LogicalOperatorDeepCopyWithNewVariablesVisitor;
 import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.VariableUtilities;
 import org.apache.hyracks.storage.am.lsm.invertedindex.api.IInvertedIndexSearchModifierFactory;
 import org.apache.hyracks.storage.am.lsm.invertedindex.search.ConjunctiveEditDistanceSearchModifierFactory;
@@ -606,21 +605,17 @@ public class InvertedIndexAccessMethod implements IAccessMethod {
         }
 
         // Create first copy.
-        Counter firstCounter = new Counter(context.getVarCounter());
-        LogicalOperatorDeepCopyVisitor firstDeepCopyVisitor = new LogicalOperatorDeepCopyVisitor(firstCounter,
-                newProbeSubTreeVarMap);
+        LogicalOperatorDeepCopyWithNewVariablesVisitor firstDeepCopyVisitor = new LogicalOperatorDeepCopyWithNewVariablesVisitor(
+                context, newProbeSubTreeVarMap);
         ILogicalOperator newProbeSubTree = firstDeepCopyVisitor.deepCopy(probeSubTree.root, null);
         inferTypes(newProbeSubTree, context);
         Mutable<ILogicalOperator> newProbeSubTreeRootRef = new MutableObject<ILogicalOperator>(newProbeSubTree);
-        context.setVarCounter(firstCounter.get());
         // Create second copy.
-        Counter secondCounter = new Counter(context.getVarCounter());
-        LogicalOperatorDeepCopyVisitor secondDeepCopyVisitor = new LogicalOperatorDeepCopyVisitor(secondCounter,
-                joinInputSubTreeVarMap);
+        LogicalOperatorDeepCopyWithNewVariablesVisitor secondDeepCopyVisitor = new LogicalOperatorDeepCopyWithNewVariablesVisitor(
+                context, joinInputSubTreeVarMap);
         ILogicalOperator joinInputSubTree = secondDeepCopyVisitor.deepCopy(probeSubTree.root, null);
         inferTypes(joinInputSubTree, context);
         probeSubTree.rootRef.setValue(joinInputSubTree);
-        context.setVarCounter(secondCounter.get());
 
         // Remember the original probe subtree reference so we can return it.
         Mutable<ILogicalOperator> originalProbeSubTreeRootRef = probeSubTree.rootRef;
@@ -634,7 +629,7 @@ public class InvertedIndexAccessMethod implements IAccessMethod {
 
         // Replace the variables in the join condition based on the mapping of variables
         // in the new probe subtree.
-        Map<LogicalVariable, LogicalVariable> varMapping = firstDeepCopyVisitor.getVariableMapping();
+        Map<LogicalVariable, LogicalVariable> varMapping = firstDeepCopyVisitor.getInputToOutputVariableMapping();
         for (Map.Entry<LogicalVariable, LogicalVariable> varMapEntry : varMapping.entrySet()) {
             if (varMapEntry.getKey() != varMapEntry.getValue()) {
                 joinCond.substituteVar(varMapEntry.getKey(), varMapEntry.getValue());
@@ -693,12 +688,11 @@ public class InvertedIndexAccessMethod implements IAccessMethod {
         VariableUtilities.getLiveVariables(indexSubTree.root, originalLiveVars);
 
         // Copy the scan subtree in indexSubTree.
-        Counter counter = new Counter(context.getVarCounter());
-        LogicalOperatorDeepCopyVisitor deepCopyVisitor = new LogicalOperatorDeepCopyVisitor(counter);
+        LogicalOperatorDeepCopyWithNewVariablesVisitor deepCopyVisitor = new LogicalOperatorDeepCopyWithNewVariablesVisitor(
+                context);
         ILogicalOperator scanSubTree = deepCopyVisitor.deepCopy(indexSubTree.root, null);
 
-        context.setVarCounter(counter.get());
-        Map<LogicalVariable, LogicalVariable> copyVarMap = deepCopyVisitor.getVariableMapping();
+        Map<LogicalVariable, LogicalVariable> copyVarMap = deepCopyVisitor.getInputToOutputVariableMapping();
         panicVarMap.putAll(copyVarMap);
 
         List<LogicalVariable> copyLiveVars = new ArrayList<LogicalVariable>();

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb/blob/e3e13735/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/subplan/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
----------------------------------------------------------------------
diff --git a/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/subplan/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/subplan/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
new file mode 100644
index 0000000..eade73f
--- /dev/null
+++ b/asterix-algebra/src/main/java/org/apache/asterix/optimizer/rules/subplan/AsterixMoveFreeVariableOperatorOutOfSubplanRule.java
@@ -0,0 +1,30 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.asterix.optimizer.rules.subplan;
+
+import org.apache.hyracks.algebricks.core.algebra.base.LogicalOperatorTag;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.MoveFreeVariableOperatorOutOfSubplanRule;
+
+public class AsterixMoveFreeVariableOperatorOutOfSubplanRule extends MoveFreeVariableOperatorOutOfSubplanRule {
+
+    @Override
+    protected boolean movableOperator(LogicalOperatorTag operatorTag) {
+        return (operatorTag == LogicalOperatorTag.ASSIGN);
+    }
+}
\ No newline at end of file


Mime
View raw message