asterixdb-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From buyin...@apache.org
Subject [3/4] incubator-asterixdb-hyracks git commit: Fix for ASTERIXDB-1018, ASTERIXDB-1017, ASTERIXDB-1019, ASTERIXDB-1020, ASTERIXDB-1029, ASTERIXDB-1030, ASTERIXDB-1034:
Date Thu, 31 Dec 2015 05:18:18 GMT
http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/util/OperatorManipulationUtil.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/util/OperatorManipulationUtil.java b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/util/OperatorManipulationUtil.java
index 61a191f..b4569e4 100644
--- a/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/util/OperatorManipulationUtil.java
+++ b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/util/OperatorManipulationUtil.java
@@ -23,7 +23,6 @@ import java.util.List;
 
 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.ILogicalOperator;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalPlan;
@@ -226,4 +225,21 @@ public class OperatorManipulationUtil {
         return op.accept(visitor, null);
     }
 
+    /**
+     * Compute type environment of a newly generated operator {@code op} and its input.
+     *
+     * @param op,
+     *            the logical operator.
+     * @param context,the
+     *            optimization context.
+     * @throws AlgebricksException
+     */
+    public static void computeTypeEnvironmentBottomUp(ILogicalOperator op, IOptimizationContext context)
+            throws AlgebricksException {
+        for (Mutable<ILogicalOperator> children : op.getInputs()) {
+            computeTypeEnvironmentBottomUp(children.getValue(), context);
+        }
+        context.computeAndSetTypeEnvironmentForOperator(op);
+    }
+
 }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/visitors/IQueryOperatorVisitor.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/visitors/IQueryOperatorVisitor.java b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/visitors/IQueryOperatorVisitor.java
new file mode 100644
index 0000000..b5ce212
--- /dev/null
+++ b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/algebra/visitors/IQueryOperatorVisitor.java
@@ -0,0 +1,59 @@
+/*
+ * 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.hyracks.algebricks.core.algebra.visitors;
+
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.DistributeResultOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.IndexInsertDeleteOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.InsertDeleteOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.SinkOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.WriteOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.WriteResultOperator;
+
+public interface IQueryOperatorVisitor<R, T> extends ILogicalOperatorVisitor<R, T> {
+
+    @Override
+    public default R visitWriteOperator(WriteOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public default R visitDistributeResultOperator(DistributeResultOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public default R visitWriteResultOperator(WriteResultOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public default R visitInsertDeleteOperator(InsertDeleteOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public default R visitIndexInsertDeleteOperator(IndexInsertDeleteOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public default R visitSinkOperator(SinkOperator op, T arg) {
+        throw new UnsupportedOperationException();
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/rewriter/base/IAlgebraicRewriteRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/rewriter/base/IAlgebraicRewriteRule.java b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/rewriter/base/IAlgebraicRewriteRule.java
index 83740de..128c372 100644
--- a/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/rewriter/base/IAlgebraicRewriteRule.java
+++ b/algebricks/algebricks-core/src/main/java/org/apache/hyracks/algebricks/core/rewriter/base/IAlgebraicRewriteRule.java
@@ -24,8 +24,34 @@ import org.apache.hyracks.algebricks.core.algebra.base.ILogicalOperator;
 import org.apache.hyracks.algebricks.core.algebra.base.IOptimizationContext;
 
 public interface IAlgebraicRewriteRule {
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException;
 
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException;
+    /**
+     * This method is invoked in pre-order traversal of a query plan.
+     *
+     * @param opRef,
+     *            the reference of the current operator to look at,
+     * @param context
+     *            the optimization context
+     * @return true if any change is introduced to the query plan; false otherwise.
+     * @throws AlgebricksException
+     */
+    public default boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
+            throws AlgebricksException {
+        return false;
+    }
+
+    /**
+     * This method is invoked in the post-order traversal of a query plan.
+     *
+     * @param opRef,
+     *            the reference of the current operator to look at,
+     * @param context
+     *            the optimization context
+     * @return true if any change is introduced to the query plan; false otherwise.
+     * @throws AlgebricksException
+     */
+    public default boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
+            throws AlgebricksException {
+        return false;
+    }
 }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-core/src/test/java/org/apache/hyracks/algebricks/core/algebra/operators/logical/visitors/EnforceVariablesVisitorTest.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-core/src/test/java/org/apache/hyracks/algebricks/core/algebra/operators/logical/visitors/EnforceVariablesVisitorTest.java b/algebricks/algebricks-core/src/test/java/org/apache/hyracks/algebricks/core/algebra/operators/logical/visitors/EnforceVariablesVisitorTest.java
new file mode 100644
index 0000000..d0676cf
--- /dev/null
+++ b/algebricks/algebricks-core/src/test/java/org/apache/hyracks/algebricks/core/algebra/operators/logical/visitors/EnforceVariablesVisitorTest.java
@@ -0,0 +1,190 @@
+/*
+ * 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.hyracks.algebricks.core.algebra.operators.logical.visitors;
+
+import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.when;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.commons.lang3.mutable.Mutable;
+import org.apache.commons.lang3.mutable.MutableObject;
+import org.apache.hyracks.algebricks.common.utils.Pair;
+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;
+import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
+import org.apache.hyracks.algebricks.core.algebra.expressions.VariableReferenceExpression;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.AggregateOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.GroupByOperator;
+import org.apache.hyracks.algebricks.core.algebra.operators.logical.ProjectOperator;
+import org.junit.Test;
+
+import junit.framework.Assert;
+
+public class EnforceVariablesVisitorTest {
+
+    /**
+     * Tests the processing of project operator in RecoverVariablesVisitor.
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testProject() throws Exception {
+        // Constructs the input operator.
+        LogicalVariable var = new LogicalVariable(1);
+        List<LogicalVariable> inputVarList = new ArrayList<>();
+        inputVarList.add(var);
+        ProjectOperator projectOp = new ProjectOperator(inputVarList);
+
+        // Constructs the visitor.
+        IOptimizationContext mockedContext = mock(IOptimizationContext.class);
+        EnforceVariablesVisitor visitor = new EnforceVariablesVisitor(mockedContext);
+
+        // Calls the visitor.
+        LogicalVariable varToEnforce = new LogicalVariable(2);
+        ProjectOperator op = (ProjectOperator) projectOp.accept(visitor,
+                Arrays.asList(new LogicalVariable[] { varToEnforce }));
+
+        // Checks the result.
+        List<LogicalVariable> expectedVars = Arrays.asList(new LogicalVariable[] { var, varToEnforce });
+        Assert.assertEquals(expectedVars, op.getVariables());
+        Assert.assertTrue(visitor.getInputVariableToOutputVariableMap().isEmpty());
+    }
+
+    /**
+     * Tests the processing of group-by operator in RecoverVariablesVisitor.
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testGroupby() throws Exception {
+        // Constructs the group-by operator.
+        LogicalVariable keyVar = new LogicalVariable(2);
+        LogicalVariable keyExprVar = new LogicalVariable(1);
+        GroupByOperator gbyOp = new GroupByOperator();
+        gbyOp.getGroupByList().add(new Pair<LogicalVariable, Mutable<ILogicalExpression>>(keyVar,
+                new MutableObject<ILogicalExpression>(new VariableReferenceExpression(keyExprVar))));
+
+        // Constructs the visitor.
+        IOptimizationContext mockedContext = mock(IOptimizationContext.class);
+        EnforceVariablesVisitor visitor = new EnforceVariablesVisitor(mockedContext);
+
+        // Calls the visitor.
+        LogicalVariable varToEnforce = new LogicalVariable(3);
+        Set<LogicalVariable> varsToEnforce = new HashSet<>();
+        varsToEnforce.add(keyExprVar);
+        varsToEnforce.add(varToEnforce);
+        GroupByOperator op = (GroupByOperator) gbyOp.accept(visitor, varsToEnforce);
+
+        // Checks the result.
+        Map<LogicalVariable, LogicalVariable> expectedVarMap = new HashMap<>();
+        expectedVarMap.put(keyExprVar, keyVar);
+        Assert.assertEquals(expectedVarMap, visitor.getInputVariableToOutputVariableMap());
+        VariableReferenceExpression decorVarExpr = (VariableReferenceExpression) op.getDecorList().get(0).second
+                .getValue();
+        Assert.assertEquals(decorVarExpr.getVariableReference(), varToEnforce);
+    }
+
+    /**
+     * Tests the processing of aggregate operator in RecoverVariablesVisitor.
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testAggregate() throws Exception {
+        // Constructs the group-by operator.
+        List<LogicalVariable> aggVars = new ArrayList<>();
+        List<Mutable<ILogicalExpression>> aggExprRefs = new ArrayList<>();
+        AggregateOperator aggOp = new AggregateOperator(aggVars, aggExprRefs);
+
+        // Constructs the visitor.
+        LogicalVariable var = new LogicalVariable(3);
+        IOptimizationContext mockedContext = mock(IOptimizationContext.class);
+        when(mockedContext.newVar()).thenReturn(var);
+        EnforceVariablesVisitor visitor = new EnforceVariablesVisitor(mockedContext);
+
+        // Calls the visitor.
+        LogicalVariable varToEnforce = new LogicalVariable(2);
+        Set<LogicalVariable> varsToEnforce = new HashSet<>();
+        varsToEnforce.add(varToEnforce);
+        GroupByOperator op = (GroupByOperator) aggOp.accept(visitor, varsToEnforce);
+
+        // Checks the result.
+        Map<LogicalVariable, LogicalVariable> expectedVarMap = new HashMap<>();
+        expectedVarMap.put(varToEnforce, var);
+        Assert.assertEquals(expectedVarMap, visitor.getInputVariableToOutputVariableMap());
+        VariableReferenceExpression keyExpr = (VariableReferenceExpression) op.getGroupByList().get(0).second
+                .getValue();
+        Assert.assertEquals(keyExpr.getVariableReference(), varToEnforce);
+        LogicalVariable expectedGbyVar = op.getGroupByList().get(0).first;
+        Assert.assertEquals(expectedGbyVar, var);
+    }
+
+    /**
+     * Tests the processing of two serial group-by operators in RecoverVariablesVisitor.
+     *
+     * @throws Exception
+     */
+    @Test
+    public void testTwoGroupbys() throws Exception {
+        // Constructs the group-by operators.
+        LogicalVariable keyVar = new LogicalVariable(1);
+        LogicalVariable keyExprVar = new LogicalVariable(2);
+        GroupByOperator gbyOp = new GroupByOperator();
+        gbyOp.getGroupByList().add(new Pair<LogicalVariable, Mutable<ILogicalExpression>>(keyVar,
+                new MutableObject<ILogicalExpression>(new VariableReferenceExpression(keyExprVar))));
+        LogicalVariable keyVar2 = new LogicalVariable(2);
+        LogicalVariable keyExprVar2 = new LogicalVariable(3);
+        GroupByOperator gbyOp2 = new GroupByOperator();
+        gbyOp.getGroupByList().add(new Pair<LogicalVariable, Mutable<ILogicalExpression>>(keyVar2,
+                new MutableObject<ILogicalExpression>(new VariableReferenceExpression(keyExprVar2))));
+        gbyOp.getInputs().add(new MutableObject<ILogicalOperator>(gbyOp2));
+
+        // Constructs the visitor.
+        IOptimizationContext mockedContext = mock(IOptimizationContext.class);
+        EnforceVariablesVisitor visitor = new EnforceVariablesVisitor(mockedContext);
+
+        // Calls the visitor.
+        LogicalVariable varToEnforce = new LogicalVariable(4);
+        Set<LogicalVariable> varsToEnforce = new HashSet<>();
+        varsToEnforce.add(keyExprVar2);
+        varsToEnforce.add(varToEnforce);
+        GroupByOperator op = (GroupByOperator) gbyOp.accept(visitor, varsToEnforce);
+
+        // Checks the result.
+        Map<LogicalVariable, LogicalVariable> expectedVarMap = new HashMap<>();
+        expectedVarMap.put(keyExprVar2, keyVar);
+        Assert.assertEquals(expectedVarMap, visitor.getInputVariableToOutputVariableMap());
+        VariableReferenceExpression decorVarExpr = (VariableReferenceExpression) op.getDecorList().get(0).second
+                .getValue();
+        Assert.assertEquals(decorVarExpr.getVariableReference(), varToEnforce);
+        GroupByOperator op2 = (GroupByOperator) op.getInputs().get(0).getValue();
+        VariableReferenceExpression decorVarExpr2 = (VariableReferenceExpression) op2.getDecorList().get(0).second
+                .getValue();
+        Assert.assertEquals(decorVarExpr2.getVariableReference(), varToEnforce);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-examples/piglet-example/src/main/java/org/apache/hyracks/algebricks/examples/piglet/rewriter/PigletRewriteRuleset.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-examples/piglet-example/src/main/java/org/apache/hyracks/algebricks/examples/piglet/rewriter/PigletRewriteRuleset.java b/algebricks/algebricks-examples/piglet-example/src/main/java/org/apache/hyracks/algebricks/examples/piglet/rewriter/PigletRewriteRuleset.java
index 6ff1477..952c7c1 100644
--- a/algebricks/algebricks-examples/piglet-example/src/main/java/org/apache/hyracks/algebricks/examples/piglet/rewriter/PigletRewriteRuleset.java
+++ b/algebricks/algebricks-examples/piglet-example/src/main/java/org/apache/hyracks/algebricks/examples/piglet/rewriter/PigletRewriteRuleset.java
@@ -27,7 +27,6 @@ import org.apache.hyracks.algebricks.rewriter.rules.BreakSelectIntoConjunctsRule
 import org.apache.hyracks.algebricks.rewriter.rules.ComplexJoinInferenceRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ConsolidateAssignsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ConsolidateSelectsRule;
-import org.apache.hyracks.algebricks.rewriter.rules.EliminateSubplanRule;
 import org.apache.hyracks.algebricks.rewriter.rules.EnforceStructuralPropertiesRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ExtractCommonOperatorsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.ExtractGbyExpressionsRule;
@@ -45,6 +44,7 @@ import org.apache.hyracks.algebricks.rewriter.rules.ReinferAllTypesRule;
 import org.apache.hyracks.algebricks.rewriter.rules.RemoveUnusedAssignAndAggregateRule;
 import org.apache.hyracks.algebricks.rewriter.rules.SetAlgebricksPhysicalOperatorsRule;
 import org.apache.hyracks.algebricks.rewriter.rules.SetExecutionModeRule;
+import org.apache.hyracks.algebricks.rewriter.rules.subplan.EliminateSubplanRule;
 
 public class PigletRewriteRuleset {
 

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanRule.java
deleted file mode 100644
index 7327e94..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanRule.java
+++ /dev/null
@@ -1,131 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.LinkedList;
-
-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.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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
-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.SubplanOperator;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorManipulationUtil;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
-import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
-
-public class EliminateSubplanRule implements IAlgebraicRewriteRule {
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context) {
-        return false;
-    }
-
-    /**
-     * Eliminate Subplan above ETS
-     * and Subplan that has only ops. with one input and no free vars. (could we
-     * modify it to consider free vars which are sources of Unnest or Assign, if
-     * there are no aggregates?)
-     */
-    @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
-        AbstractLogicalOperator op = (AbstractLogicalOperator) opRef.getValue();
-        if (op.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-            return false;
-        }
-        SubplanOperator subplan = (SubplanOperator) op;
-
-        Mutable<ILogicalOperator> outerRef = subplan.getInputs().get(0);
-        AbstractLogicalOperator outerRefOp = (AbstractLogicalOperator) outerRef.getValue();
-        if (outerRefOp.getOperatorTag() == LogicalOperatorTag.EMPTYTUPLESOURCE) {
-            elimSubplanOverEts(opRef, context);
-            return true;
-        }
-        if (subplan.getNestedPlans().size() == 1 && subplan.getNestedPlans().get(0).getRoots().size() == 1
-                && !OperatorPropertiesUtil.hasFreeVariables(subplan)) {
-            if (elimOneSubplanWithNoFreeVars(opRef)) {
-                return true;
-            }
-        }
-
-        return false;
-    }
-
-    private boolean elimOneSubplanWithNoFreeVars(Mutable<ILogicalOperator> opRef) {
-        SubplanOperator subplan = (SubplanOperator) opRef.getValue();
-        AbstractLogicalOperator rootOp = (AbstractLogicalOperator) subplan.getNestedPlans().get(0).getRoots().get(0)
-                .getValue();
-        if (rootOp.getOperatorTag() == LogicalOperatorTag.EMPTYTUPLESOURCE
-                || rootOp.getOperatorTag() == LogicalOperatorTag.NESTEDTUPLESOURCE) {
-            opRef.setValue(subplan.getInputs().get(0).getValue());
-            return true;
-        } else {
-            AbstractLogicalOperator botOp = rootOp;
-            if (botOp.getInputs().size() != 1) {
-                return false;
-            }
-            do {
-                Mutable<ILogicalOperator> botRef = botOp.getInputs().get(0);
-                botOp = (AbstractLogicalOperator) botRef.getValue();
-                if (botOp.getOperatorTag() == LogicalOperatorTag.EMPTYTUPLESOURCE) {
-                    botRef.setValue(subplan.getInputs().get(0).getValue());
-                    opRef.setValue(rootOp);
-                    return true;
-                }
-            } while (botOp.getInputs().size() == 1);
-            return false;
-        }
-    }
-
-    private void elimSubplanOverEts(Mutable<ILogicalOperator> opRef, IOptimizationContext ctx)
-            throws AlgebricksException {
-        SubplanOperator subplan = (SubplanOperator) opRef.getValue();
-        for (ILogicalPlan p : subplan.getNestedPlans()) {
-            for (Mutable<ILogicalOperator> r : p.getRoots()) {
-                OperatorManipulationUtil.ntsToEts(r, ctx);
-            }
-        }
-        LinkedList<Mutable<ILogicalOperator>> allRoots = subplan.allRootsInReverseOrder();
-        if (allRoots.size() == 1) {
-            opRef.setValue(allRoots.get(0).getValue());
-        } else {
-            ILogicalOperator topOp = null;
-            for (Mutable<ILogicalOperator> r : allRoots) {
-                if (topOp == null) {
-                    topOp = r.getValue();
-                } else {
-                    LeftOuterJoinOperator j = new LeftOuterJoinOperator(new MutableObject<ILogicalExpression>(
-                            ConstantExpression.TRUE));
-                    j.getInputs().add(new MutableObject<ILogicalOperator>(topOp));
-                    j.getInputs().add(r);
-                    ctx.setOutputTypeEnvironment(j, j.computeOutputTypeEnvironment(ctx));
-                    topOp = j;
-                }
-            }
-            opRef.setValue(topOp);
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanWithInputCardinalityOneRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanWithInputCardinalityOneRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanWithInputCardinalityOneRule.java
deleted file mode 100644
index df6e1ee..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/EliminateSubplanWithInputCardinalityOneRule.java
+++ /dev/null
@@ -1,203 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.ArrayList;
-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.ListSet;
-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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SubplanOperator;
-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;
-
-/**
- * This rule eliminates a subplan with the following pattern:
- * -- SUBPLAN
- * -- OP (where OP produces exactly one tuple)
- * The live variables at OP will not be used after SUBPLAN.
- * Note: This rule must be applied after
- * the RemoveRedundantVariablesRule (to avoid the lineage analysis of variable cardinality).
- * 
- * @author yingyib
- */
-public class EliminateSubplanWithInputCardinalityOneRule implements IAlgebraicRewriteRule {
-    /** The pointer to the topmost operator */
-    private Mutable<ILogicalOperator> rootRef;
-    /** Whether the rule has even been invoked */
-    private boolean invoked = false;
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context) {
-        return false;
-    }
-
-    @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
-        if (!invoked) {
-            rootRef = opRef;
-            invoked = true;
-        }
-        AbstractLogicalOperator op = (AbstractLogicalOperator) opRef.getValue();
-        if (op.getInputs().size() <= 0) {
-            return false;
-        }
-        boolean changed = false;
-        for (Mutable<ILogicalOperator> subplanRef : op.getInputs()) {
-            AbstractLogicalOperator op1 = (AbstractLogicalOperator) subplanRef.getValue();
-            if (op1.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-                continue;
-            }
-
-            SubplanOperator subplan = (SubplanOperator) op1;
-            Set<LogicalVariable> usedVarsUp = new ListSet<LogicalVariable>();
-            OperatorPropertiesUtil.getFreeVariablesInPath(rootRef.getValue(), subplan, usedVarsUp);
-            // TODO(buyingyi): figure out the rewriting for subplan operators with multiple subplans.
-            if (subplan.getNestedPlans().size() != 1) {
-                continue;
-            }
-
-            ILogicalOperator subplanInputOperator = subplan.getInputs().get(0).getValue();
-            Set<LogicalVariable> subplanInputVars = new ListSet<LogicalVariable>();
-            VariableUtilities.getLiveVariables(subplanInputOperator, subplanInputVars);
-            int subplanInputVarSize = subplanInputVars.size();
-            subplanInputVars.removeAll(usedVarsUp);
-            // Makes sure the free variables are only used in the subplan.
-            if (subplanInputVars.size() < subplanInputVarSize) {
-                continue;
-            }
-            Set<LogicalVariable> freeVars = new ListSet<LogicalVariable>();
-            OperatorPropertiesUtil.getFreeVariablesInSubplans(subplan, freeVars);
-            boolean cardinalityOne = isCardinalityOne(subplan.getInputs().get(0), freeVars);
-            if (cardinalityOne) {
-                /** If the cardinality of freeVars in the subplan is one, the subplan can be removed. */
-                ILogicalPlan plan = subplan.getNestedPlans().get(0);
-
-                List<Mutable<ILogicalOperator>> rootRefs = plan.getRoots();
-                // TODO(buyingyi): investigate the case of multi-root plans.
-                if (rootRefs.size() != 1) {
-                    continue;
-                }
-                Set<Mutable<ILogicalOperator>> ntsSet = new ListSet<Mutable<ILogicalOperator>>();
-                findNts(rootRefs.get(0), ntsSet);
-
-                /** Replaces nts with the input operator of the subplan. */
-                for (Mutable<ILogicalOperator> nts : ntsSet) {
-                    nts.setValue(subplanInputOperator);
-                }
-                subplanRef.setValue(rootRefs.get(0).getValue());
-                changed = true;
-            } else {
-                continue;
-            }
-        }
-        return changed;
-    }
-
-    /**
-     * Whether the cardinality of the input free variables are one.
-     * 
-     * @param opRef
-     *            the operator to be checked (including its input operators)
-     * @param freeVars
-     *            variables to be checked for produced operators
-     * @return true if every input variable has cardinality one; false otherwise.
-     * @throws AlgebricksException
-     */
-    private boolean isCardinalityOne(Mutable<ILogicalOperator> opRef, Set<LogicalVariable> freeVars)
-            throws AlgebricksException {
-        Set<LogicalVariable> varsWithCardinalityOne = new ListSet<LogicalVariable>();
-        Set<LogicalVariable> varsLiveAtUnnestAndJoin = new ListSet<LogicalVariable>();
-        isCardinalityOne(opRef, freeVars, varsWithCardinalityOne, varsLiveAtUnnestAndJoin);
-        varsWithCardinalityOne.removeAll(varsLiveAtUnnestAndJoin);
-        return varsWithCardinalityOne.equals(freeVars);
-    }
-
-    /**
-     * Recursively adding variables which has cardinality one and in int the input free variable set.
-     * 
-     * @param opRef
-     *            , the current operator reference.
-     * @param freeVars
-     *            , a set of variables.
-     * @param varsWithCardinalityOne
-     *            , variables in the free variable set with cardinality one at the time they are created.
-     * @param varsLiveAtUnnestAndJoin
-     *            , live variables at Unnest and Join. The cardinalities of those variables can become more than one
-     *            even if their cardinalities were one at the time those variables were created.
-     * @throws AlgebricksException
-     */
-    private void isCardinalityOne(Mutable<ILogicalOperator> opRef, Set<LogicalVariable> freeVars,
-            Set<LogicalVariable> varsWithCardinalityOne, Set<LogicalVariable> varsLiveAtUnnestAndJoin)
-            throws AlgebricksException {
-        AbstractLogicalOperator operator = (AbstractLogicalOperator) opRef.getValue();
-        List<LogicalVariable> producedVars = new ArrayList<LogicalVariable>();
-        VariableUtilities.getProducedVariables(operator, producedVars);
-        if (operator.getOperatorTag() == LogicalOperatorTag.UNNEST
-                || operator.getOperatorTag() == LogicalOperatorTag.INNERJOIN
-                || operator.getOperatorTag() == LogicalOperatorTag.LEFTOUTERJOIN) {
-            VariableUtilities.getLiveVariables(operator, varsLiveAtUnnestAndJoin);
-        }
-        if (operator.getOperatorTag() == LogicalOperatorTag.AGGREGATE) {
-            for (LogicalVariable producedVar : producedVars) {
-                if (freeVars.contains(producedVar)) {
-                    varsWithCardinalityOne.add(producedVar);
-                }
-            }
-        }
-        if (varsWithCardinalityOne.size() == freeVars.size()) {
-            return;
-        }
-        for (Mutable<ILogicalOperator> childRef : operator.getInputs()) {
-            isCardinalityOne(childRef, freeVars, varsWithCardinalityOne, varsLiveAtUnnestAndJoin);
-        }
-    }
-
-    /**
-     * Find the NestedTupleSource operator in the direct/undirect input operators of opRef.
-     * 
-     * @param opRef
-     *            , the current operator reference.
-     * @param ntsSet
-     *            , the set NestedTupleSource operator references.
-     */
-    private void findNts(Mutable<ILogicalOperator> opRef, Set<Mutable<ILogicalOperator>> ntsSet) {
-        int childSize = opRef.getValue().getInputs().size();
-        if (childSize == 0) {
-            AbstractLogicalOperator op = (AbstractLogicalOperator) opRef.getValue();
-            if (op.getOperatorTag() == LogicalOperatorTag.NESTEDTUPLESOURCE) {
-                ntsSet.add(opRef);
-            }
-            return;
-        }
-        for (Mutable<ILogicalOperator> childRef : opRef.getValue().getInputs()) {
-            findNts(childRef, ntsSet);
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InlineVariablesRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InlineVariablesRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InlineVariablesRule.java
index 1ecb893..f2645f5 100644
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InlineVariablesRule.java
+++ b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InlineVariablesRule.java
@@ -85,7 +85,8 @@ public class InlineVariablesRule implements IAlgebraicRewriteRule {
     }
 
     @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
+    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
+            throws AlgebricksException {
         if (hasRun) {
             return false;
         }
@@ -145,7 +146,7 @@ public class InlineVariablesRule implements IAlgebraicRewriteRule {
             List<Mutable<ILogicalExpression>> exprs = assignOp.getExpressions();
             for (int i = 0; i < vars.size(); i++) {
                 ILogicalExpression expr = exprs.get(i).getValue();
-                // Ignore functions that are either in the doNotInline set or are non-functional               
+                // Ignore functions that are either in the doNotInline set or are non-functional
                 if (expr.getExpressionTag() == LogicalExpressionTag.FUNCTION_CALL) {
                     AbstractFunctionCallExpression funcExpr = (AbstractFunctionCallExpression) expr;
                     if (doNotInlineFuncs.contains(funcExpr.getFunctionIdentifier())
@@ -174,6 +175,14 @@ public class InlineVariablesRule implements IAlgebraicRewriteRule {
             }
         }
 
+        // References to variables generated in the right branch of a left-outer-join cannot be inlined
+        // in operators above the left-outer-join.
+        if (op.getOperatorTag() == LogicalOperatorTag.LEFTOUTERJOIN) {
+            Set<LogicalVariable> rightLiveVars = new HashSet<LogicalVariable>();
+            VariableUtilities.getLiveVariables(op.getInputs().get(1).getValue(), rightLiveVars);
+            varAssignRhs.keySet().removeAll(rightLiveVars);
+        }
+
         if (performBottomUpAction(op)) {
             modified = true;
         }

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InsertOuterJoinRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InsertOuterJoinRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InsertOuterJoinRule.java
deleted file mode 100644
index b8c75bd..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/InsertOuterJoinRule.java
+++ /dev/null
@@ -1,125 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.Iterator;
-
-import org.apache.commons.lang3.mutable.Mutable;
-
-import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
-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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.InnerJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.LeftOuterJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SubplanOperator;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
-import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
-
-public class InsertOuterJoinRule implements IAlgebraicRewriteRule {
-
-    @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
-        return false;
-    }
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException {
-        AbstractLogicalOperator op0 = (AbstractLogicalOperator) opRef.getValue();
-        if (op0.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-            return false;
-        }
-        SubplanOperator subplan = (SubplanOperator) op0;
-
-        Iterator<ILogicalPlan> plansIter = subplan.getNestedPlans().iterator();
-        ILogicalPlan p = null;
-        while (plansIter.hasNext()) {
-            p = plansIter.next();
-        }
-        if (p == null) {
-            return false;
-        }
-        if (p.getRoots().size() != 1) {
-            return false;
-        }
-        Mutable<ILogicalOperator> subplanRoot = p.getRoots().get(0);
-        AbstractLogicalOperator op1 = (AbstractLogicalOperator) subplanRoot.getValue();
-        Mutable<ILogicalOperator> opUnder = subplan.getInputs().get(0);
-
-        if (OperatorPropertiesUtil.isNullTest((AbstractLogicalOperator) opUnder.getValue())) {
-            return false;
-        }
-
-        switch (op1.getOperatorTag()) {
-            case INNERJOIN: {
-                InnerJoinOperator join = (InnerJoinOperator) op1;
-                Mutable<ILogicalOperator> leftRef = join.getInputs().get(0);
-                Mutable<ILogicalOperator> rightRef = join.getInputs().get(1);
-                Mutable<ILogicalOperator> ntsRef = getNtsAtEndOfPipeline(leftRef);
-                if (ntsRef == null) {
-                    ntsRef = getNtsAtEndOfPipeline(rightRef);
-                    if (ntsRef == null) {
-                        return false;
-                    } else {
-                        Mutable<ILogicalOperator> t = leftRef;
-                        leftRef = rightRef;
-                        rightRef = t;
-                    }
-                }
-                ntsRef.setValue(opUnder.getValue());
-                LeftOuterJoinOperator loj = new LeftOuterJoinOperator(join.getCondition());
-                loj.getInputs().add(leftRef);
-                loj.getInputs().add(rightRef);
-                opRef.setValue(loj);
-                context.computeAndSetTypeEnvironmentForOperator(loj);
-                return true;
-            }
-            case LEFTOUTERJOIN: {
-                LeftOuterJoinOperator join = (LeftOuterJoinOperator) op1;
-                Mutable<ILogicalOperator> leftRef = join.getInputs().get(0);
-                Mutable<ILogicalOperator> ntsRef = getNtsAtEndOfPipeline(leftRef);
-                if (ntsRef == null) {
-                    return false;
-                }
-                ntsRef.setValue(opUnder.getValue());
-                opRef.setValue(join);
-                context.computeAndSetTypeEnvironmentForOperator(join);
-                return true;
-            }
-            default: {
-                return false;
-            }
-        }
-    }
-
-    private Mutable<ILogicalOperator> getNtsAtEndOfPipeline(Mutable<ILogicalOperator> opRef) {
-        AbstractLogicalOperator op = (AbstractLogicalOperator) opRef.getValue();
-        if (op.getOperatorTag() == LogicalOperatorTag.NESTEDTUPLESOURCE) {
-            return opRef;
-        }
-        if (op.getInputs().size() != 1) {
-            return null;
-        }
-        return getNtsAtEndOfPipeline(op.getInputs().get(0));
-    }
-
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/IntroduceGroupByForSubplanRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/IntroduceGroupByForSubplanRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/IntroduceGroupByForSubplanRule.java
deleted file mode 100644
index 67e8d42..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/IntroduceGroupByForSubplanRule.java
+++ /dev/null
@@ -1,327 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-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.ListSet;
-import org.apache.hyracks.algebricks.common.utils.Pair;
-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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ScalarFunctionCallExpression;
-import org.apache.hyracks.algebricks.core.algebra.expressions.VariableReferenceExpression;
-import org.apache.hyracks.algebricks.core.algebra.functions.AlgebricksBuiltinFunctions;
-import org.apache.hyracks.algebricks.core.algebra.functions.IFunctionInfo;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractBinaryJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
-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.GroupByOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.NestedTupleSourceOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.ProjectOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SelectOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SubplanOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.UnnestOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.VariableUtilities;
-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.util.OperatorManipulationUtil;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
-import org.apache.hyracks.algebricks.core.config.AlgebricksConfig;
-import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
-import org.apache.hyracks.algebricks.rewriter.util.PhysicalOptimizationsUtil;
-
-/**
- * The rule searches for SUBPLAN operator with a optional PROJECT operator and
- * an AGGREGATE followed by a join operator.
- *
- * <pre>
- * Before
- * 
- *   plan__parent
- *   SUBPLAN {
- *     PROJECT?
- *     AGGREGATE
- *     plan__nested_A
- *     INNER_JOIN | LEFT_OUTER_JOIN ($condition, $left, $right)
- *       plan__nested_B
- *   }
- *   plan__child
- * 
- *   where $condition does not equal a constant true.
- * 
- * After (This is a general application of the rule, specifics may vary based on the query plan.)
- * 
- *   plan__parent
- *   GROUP_BY {
- *     PROJECT?
- *     AGGREGATE
- *     plan__nested_A
- *     SELECT( algebricks:not( is_null( $right ) ) )
- *     NESTED_TUPLE_SOURCE
- *   }
- *   SUBPLAN {
- *     INNER_JOIN | LEFT_OUTER_JOIN ($condition, $left, $right)
- *       plan__nested_B
- *   }
- *   plan__child
- * </pre>
- *
- * @author prestonc
- */
-
-public class IntroduceGroupByForSubplanRule implements IAlgebraicRewriteRule {
-
-    @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context) throws AlgebricksException {
-        return false;
-    }
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException {
-        AbstractLogicalOperator op0 = (AbstractLogicalOperator) opRef.getValue();
-        if (op0.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-            return false;
-        }
-        SubplanOperator subplan = (SubplanOperator) op0;
-
-        Iterator<ILogicalPlan> plansIter = subplan.getNestedPlans().iterator();
-        ILogicalPlan p = null;
-        while (plansIter.hasNext()) {
-            p = plansIter.next();
-        }
-        if (p == null) {
-            return false;
-        }
-        if (p.getRoots().size() != 1) {
-            return false;
-        }
-        Mutable<ILogicalOperator> subplanRoot = p.getRoots().get(0);
-        AbstractLogicalOperator op1 = (AbstractLogicalOperator) subplanRoot.getValue();
-
-        Mutable<ILogicalOperator> botRef = subplanRoot;
-        AbstractLogicalOperator op2;
-        // Project is optional
-        if (op1.getOperatorTag() != LogicalOperatorTag.PROJECT) {
-            op2 = op1;
-        } else {
-            ProjectOperator project = (ProjectOperator) op1;
-            botRef = project.getInputs().get(0);
-            op2 = (AbstractLogicalOperator) botRef.getValue();
-        }
-        if (op2.getOperatorTag() != LogicalOperatorTag.AGGREGATE) {
-            return false;
-        }
-        AggregateOperator aggregate = (AggregateOperator) op2;
-
-        Set<LogicalVariable> free = new HashSet<LogicalVariable>();
-        VariableUtilities.getUsedVariables(aggregate, free);
-
-        Mutable<ILogicalOperator> op3Ref = aggregate.getInputs().get(0);
-        AbstractLogicalOperator op3 = (AbstractLogicalOperator) op3Ref.getValue();
-
-        while (op3.getInputs().size() == 1) {
-            Set<LogicalVariable> prod = new HashSet<LogicalVariable>();
-            VariableUtilities.getProducedVariables(op3, prod);
-            free.removeAll(prod);
-            VariableUtilities.getUsedVariables(op3, free);
-            botRef = op3Ref;
-            op3Ref = op3.getInputs().get(0);
-            op3 = (AbstractLogicalOperator) op3Ref.getValue();
-        }
-
-        if (op3.getOperatorTag() != LogicalOperatorTag.INNERJOIN
-                && op3.getOperatorTag() != LogicalOperatorTag.LEFTOUTERJOIN) {
-            return false;
-        }
-        AbstractBinaryJoinOperator join = (AbstractBinaryJoinOperator) op3;
-        if (join.getCondition().getValue() == ConstantExpression.TRUE) {
-            return false;
-        }
-        VariableUtilities.getUsedVariables(join, free);
-
-        AbstractLogicalOperator b0 = (AbstractLogicalOperator) join.getInputs().get(0).getValue();
-        // see if there's an NTS at the end of the pipeline
-        NestedTupleSourceOperator outerNts = getNts(b0);
-        if (outerNts == null) {
-            AbstractLogicalOperator b1 = (AbstractLogicalOperator) join.getInputs().get(1).getValue();
-            outerNts = getNts(b1);
-            if (outerNts == null) {
-                return false;
-            }
-        }
-
-        Set<LogicalVariable> pkVars = computeGbyVars(outerNts, free, context);
-        if (pkVars == null || pkVars.size() < 1) {
-            // there is no non-trivial primary key, group-by keys are all live variables
-            ILogicalOperator subplanInput = subplan.getInputs().get(0).getValue();
-            pkVars = new HashSet<LogicalVariable>();
-            VariableUtilities.getLiveVariables(subplanInput, pkVars);
-        }
-        AlgebricksConfig.ALGEBRICKS_LOGGER.fine("Found FD for introducing group-by: " + pkVars);
-
-        Mutable<ILogicalOperator> rightRef = join.getInputs().get(1);
-        LogicalVariable testForNull = null;
-        AbstractLogicalOperator right = (AbstractLogicalOperator) rightRef.getValue();
-        switch (right.getOperatorTag()) {
-            case UNNEST: {
-                UnnestOperator innerUnnest = (UnnestOperator) right;
-                // Select [ $y != null ]
-                testForNull = innerUnnest.getVariable();
-                break;
-            }
-            case RUNNINGAGGREGATE: {
-                ILogicalOperator inputToRunningAggregate = right.getInputs().get(0).getValue();
-                Set<LogicalVariable> producedVars = new ListSet<LogicalVariable>();
-                VariableUtilities.getProducedVariables(inputToRunningAggregate, producedVars);
-                if (!producedVars.isEmpty()) {
-                    // Select [ $y != null ]
-                    testForNull = producedVars.iterator().next();
-                }
-                break;
-            }
-            case DATASOURCESCAN: {
-                DataSourceScanOperator innerScan = (DataSourceScanOperator) right;
-                // Select [ $y != null ]
-                if (innerScan.getVariables().size() == 1) {
-                    testForNull = innerScan.getVariables().get(0);
-                }
-                break;
-            }
-        }
-        if (testForNull == null) {
-            testForNull = context.newVar();
-            AssignOperator tmpAsgn = new AssignOperator(testForNull, new MutableObject<ILogicalExpression>(
-                    ConstantExpression.TRUE));
-            tmpAsgn.getInputs().add(new MutableObject<ILogicalOperator>(rightRef.getValue()));
-            rightRef.setValue(tmpAsgn);
-            context.computeAndSetTypeEnvironmentForOperator(tmpAsgn);
-        }
-
-        IFunctionInfo finfoEq = context.getMetadataProvider().lookupFunction(AlgebricksBuiltinFunctions.IS_NULL);
-        ILogicalExpression isNullTest = new ScalarFunctionCallExpression(finfoEq,
-                new MutableObject<ILogicalExpression>(new VariableReferenceExpression(testForNull)));
-        IFunctionInfo finfoNot = context.getMetadataProvider().lookupFunction(AlgebricksBuiltinFunctions.NOT);
-        ScalarFunctionCallExpression nonNullTest = new ScalarFunctionCallExpression(finfoNot,
-                new MutableObject<ILogicalExpression>(isNullTest));
-        SelectOperator selectNonNull = new SelectOperator(new MutableObject<ILogicalExpression>(nonNullTest), false,
-                null);
-        GroupByOperator g = new GroupByOperator();
-        Mutable<ILogicalOperator> newSubplanRef = new MutableObject<ILogicalOperator>(subplan);
-        NestedTupleSourceOperator nts = new NestedTupleSourceOperator(new MutableObject<ILogicalOperator>(g));
-        opRef.setValue(g);
-        selectNonNull.getInputs().add(new MutableObject<ILogicalOperator>(nts));
-
-        List<Mutable<ILogicalOperator>> prodInpList = botRef.getValue().getInputs();
-        prodInpList.clear();
-        prodInpList.add(new MutableObject<ILogicalOperator>(selectNonNull));
-
-        ILogicalPlan gPlan = new ALogicalPlanImpl(new MutableObject<ILogicalOperator>(subplanRoot.getValue()));
-        g.getNestedPlans().add(gPlan);
-        subplanRoot.setValue(op3Ref.getValue());
-        g.getInputs().add(newSubplanRef);
-
-        HashSet<LogicalVariable> underVars = new HashSet<LogicalVariable>();
-        VariableUtilities.getLiveVariables(subplan.getInputs().get(0).getValue(), underVars);
-        underVars.removeAll(pkVars);
-        Map<LogicalVariable, LogicalVariable> mappedVars = buildVarExprList(pkVars, context, g, g.getGroupByList());
-        context.updatePrimaryKeys(mappedVars);
-        for (LogicalVariable uv : underVars) {
-            g.getDecorList().add(
-                    new Pair<LogicalVariable, Mutable<ILogicalExpression>>(null, new MutableObject<ILogicalExpression>(
-                            new VariableReferenceExpression(uv))));
-        }
-        OperatorPropertiesUtil.typeOpRec(subplanRoot, context);
-        OperatorPropertiesUtil.typeOpRec(gPlan.getRoots().get(0), context);
-        context.computeAndSetTypeEnvironmentForOperator(g);
-        return true;
-    }
-
-    private NestedTupleSourceOperator getNts(AbstractLogicalOperator op) {
-        AbstractLogicalOperator alo = op;
-        do {
-            if (alo.getOperatorTag() == LogicalOperatorTag.NESTEDTUPLESOURCE) {
-                return (NestedTupleSourceOperator) alo;
-            }
-            if (alo.getInputs().size() != 1) {
-                return null;
-            }
-            alo = (AbstractLogicalOperator) alo.getInputs().get(0).getValue();
-        } while (true);
-    }
-
-    protected Set<LogicalVariable> computeGbyVars(AbstractLogicalOperator op, Set<LogicalVariable> freeVars,
-            IOptimizationContext context) throws AlgebricksException {
-        PhysicalOptimizationsUtil.computeFDsAndEquivalenceClasses(op, context);
-        List<FunctionalDependency> fdList = context.getFDList(op);
-        if (fdList == null) {
-            return null;
-        }
-        // check if any of the FDs is a key
-        List<LogicalVariable> all = new ArrayList<LogicalVariable>();
-        VariableUtilities.getLiveVariables(op, all);
-        all.retainAll(freeVars);
-        for (FunctionalDependency fd : fdList) {
-            if (fd.getTail().containsAll(all)) {
-                return new HashSet<LogicalVariable>(fd.getHead());
-            }
-        }
-        return null;
-    }
-
-    private Map<LogicalVariable, LogicalVariable> buildVarExprList(Collection<LogicalVariable> vars,
-            IOptimizationContext context, GroupByOperator g,
-            List<Pair<LogicalVariable, Mutable<ILogicalExpression>>> outVeList) throws AlgebricksException {
-        Map<LogicalVariable, LogicalVariable> m = new HashMap<LogicalVariable, LogicalVariable>();
-        for (LogicalVariable ov : vars) {
-            LogicalVariable newVar = context.newVar();
-            ILogicalExpression varExpr = new VariableReferenceExpression(newVar);
-            outVeList.add(new Pair<LogicalVariable, Mutable<ILogicalExpression>>(ov,
-                    new MutableObject<ILogicalExpression>(varExpr)));
-            for (ILogicalPlan p : g.getNestedPlans()) {
-                for (Mutable<ILogicalOperator> r : p.getRoots()) {
-                    OperatorManipulationUtil.substituteVarRec((AbstractLogicalOperator) r.getValue(), ov, newVar, true,
-                            context);
-                }
-            }
-            AbstractLogicalOperator opUnder = (AbstractLogicalOperator) g.getInputs().get(0).getValue();
-            OperatorManipulationUtil.substituteVarRec(opUnder, ov, newVar, true, context);
-            m.put(ov, newVar);
-        }
-        return m;
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/MoveFreeVariableOperatorOutOfSubplanRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/MoveFreeVariableOperatorOutOfSubplanRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/MoveFreeVariableOperatorOutOfSubplanRule.java
deleted file mode 100644
index 06063b8..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/MoveFreeVariableOperatorOutOfSubplanRule.java
+++ /dev/null
@@ -1,186 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.HashSet;
-import java.util.ListIterator;
-import java.util.Set;
-
-import org.apache.commons.lang3.mutable.Mutable;
-
-import org.apache.hyracks.algebricks.common.exceptions.AlgebricksException;
-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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.SubplanOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.visitors.VariableUtilities;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
-
-/**
- * The rule searches for operators that can be moved outside the subplan.
- *
- * <pre>
- * Before
- * 
- *   %PARENT_PLAN
- *   SUBPLAN{
- *     %NESTED_OPERATORS_B+
- *     ASSIGN || %SUBPLAN
- *     %NESTED_OPERATORS_A*
- *     NESTEDTUPLESOURCE
- *   }
- *   %CHILD_PLAN
- * 
- *   where
- *     %SUBPLAN has one nested plan with a root AGGREGATE operator.
- * 
- * After
- * 
- *   %PARENT_PLAN
- *   SUBPLAN{
- *     %NESTED_OPERATORS_B+
- *     %NESTED_OPERATORS_A*
- *     NESTEDTUPLESOURCE
- *   }
- *   ASSIGN || %SUBPLAN
- *   %CHILD_PLAN
- * </pre>
- */
-public class MoveFreeVariableOperatorOutOfSubplanRule extends AbstractDecorrelationRule {
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException {
-        AbstractLogicalOperator op0 = (AbstractLogicalOperator) opRef.getValue();
-        if (op0.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-            return false;
-        }
-        SubplanOperator subplan = (SubplanOperator) op0;
-
-        Mutable<ILogicalOperator> leftRef = subplan.getInputs().get(0);
-        if (((AbstractLogicalOperator) leftRef.getValue()).getOperatorTag() == LogicalOperatorTag.EMPTYTUPLESOURCE) {
-            return false;
-        }
-
-        ListIterator<ILogicalPlan> plansIter = subplan.getNestedPlans().listIterator();
-        ILogicalPlan p = null;
-        while (plansIter.hasNext()) {
-            p = plansIter.next();
-        }
-        if (p == null) {
-            return false;
-        }
-        if (p.getRoots().size() != 1) {
-            return false;
-        }
-        Mutable<ILogicalOperator> opRef1 = p.getRoots().get(0);
-
-        //The root operator will not be movable. Start with the second op
-        AbstractLogicalOperator op1 = (AbstractLogicalOperator) opRef1.getValue();
-        if (op1.getInputs().size() != 1) {
-            return false;
-        }
-        Mutable<ILogicalOperator> op2Ref = op1.getInputs().get(0);
-
-        //Get all variables that come from outside of the loop
-        Set<LogicalVariable> free = new HashSet<LogicalVariable>();
-        OperatorPropertiesUtil.getFreeVariablesInSelfOrDesc(op1, free);
-
-        while (op2Ref != null) {
-            //Get the operator that we want to look at
-            AbstractLogicalOperator op2 = (AbstractLogicalOperator) op2Ref.getValue();
-
-            //Make sure we are looking at subplan with a scan/join
-            if (op2.getInputs().size() != 1 || !descOrSelfIsScanOrJoin(op2)) {
-                return false;
-            }
-            boolean notApplicable = false;
-
-            //Get its used variables
-            Set<LogicalVariable> used = new HashSet<LogicalVariable>();
-
-            //not movable if the operator is not an assign or subplan
-            //Might be helpful in the future for other operations in the future
-            if (movableOperator(op2.getOperatorTag())) {
-                if (op2.getOperatorTag() == LogicalOperatorTag.ASSIGN) {
-                    VariableUtilities.getUsedVariables(op2, used);
-                } else if (op2.getOperatorTag() == LogicalOperatorTag.SUBPLAN) {
-                    // Nested plan must have an aggregate root.
-                    ListIterator<ILogicalPlan> subplansIter = ((SubplanOperator) op2).getNestedPlans().listIterator();
-                    ILogicalPlan plan = null;
-                    while (subplansIter.hasNext()) {
-                        plan = subplansIter.next();
-                    }
-                    if (plan == null) {
-                        return false;
-                    }
-                    if (plan.getRoots().size() != 1) {
-                        return false;
-                    }
-                    ILogicalOperator op3 = plan.getRoots().get(0).getValue();
-                    if (op3.getOperatorTag() != LogicalOperatorTag.AGGREGATE) {
-                        return false;
-                    }
-                    // Used variables do not include ones created in the subplan.
-                    VariableUtilities.getUsedVariables(op2, used);
-                    Set<LogicalVariable> subplanProducedAndDown = new HashSet<LogicalVariable>();
-                    VariableUtilities.getProducedVariablesInDescendantsAndSelf(op3, subplanProducedAndDown);
-                    used.removeAll(subplanProducedAndDown);
-                } else {
-                    notApplicable = true;
-                }
-            } else {
-                notApplicable = true;
-            }
-
-            //Make sure that all of its used variables come from outside
-            for (LogicalVariable var : used) {
-                if (!free.contains(var)) {
-                    notApplicable = true;
-                }
-            }
-
-            if (notApplicable) {
-                op2Ref = op2.getInputs().get(0);
-            } else {
-                //Make the input of op2 be the input of op1
-                op2Ref.setValue(op2.getInputs().get(0).getValue());
-
-                //Make the outside of the subplan the input of op2
-                Mutable<ILogicalOperator> outsideRef = op2.getInputs().get(0);
-                outsideRef.setValue(op0.getInputs().get(0).getValue());
-
-                //Make op2 the input of the subplan
-                Mutable<ILogicalOperator> op2OutsideRef = op0.getInputs().get(0);
-                op2OutsideRef.setValue(op2);
-
-                return true;
-            }
-
-        }
-        return false;
-    }
-
-    protected boolean movableOperator(LogicalOperatorTag operatorTag) {
-        return (operatorTag == LogicalOperatorTag.ASSIGN || operatorTag == LogicalOperatorTag.SUBPLAN);
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/NestedSubplanToJoinRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/NestedSubplanToJoinRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/NestedSubplanToJoinRule.java
deleted file mode 100644
index f8a93b0..0000000
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/NestedSubplanToJoinRule.java
+++ /dev/null
@@ -1,146 +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.hyracks.algebricks.rewriter.rules;
-
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-
-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.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.LogicalOperatorTag;
-import org.apache.hyracks.algebricks.core.algebra.base.LogicalVariable;
-import org.apache.hyracks.algebricks.core.algebra.expressions.ConstantExpression;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractLogicalOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.AbstractOperatorWithNestedPlans;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.EmptyTupleSourceOperator;
-import org.apache.hyracks.algebricks.core.algebra.operators.logical.InnerJoinOperator;
-import org.apache.hyracks.algebricks.core.algebra.util.OperatorPropertiesUtil;
-import org.apache.hyracks.algebricks.core.rewriter.base.IAlgebraicRewriteRule;
-
-/**
- * replace Subplan operators with nested loop joins where the join condition is true, if the Subplan
- * does not contain free variables (does not have correlations to the input stream).
- *
- * @author yingyib
- */
-public class NestedSubplanToJoinRule implements IAlgebraicRewriteRule {
-
-    @Override
-    public boolean rewritePre(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException {
-        return false;
-    }
-
-    @Override
-    public boolean rewritePost(Mutable<ILogicalOperator> opRef, IOptimizationContext context)
-            throws AlgebricksException {
-        if (context.checkIfInDontApplySet(this, opRef.getValue()))
-            return false;
-        context.addToDontApplySet(this, opRef.getValue());
-
-        ILogicalOperator op1 = opRef.getValue();
-        if (op1.getInputs().size() == 0) {
-            return false;
-        }
-
-        boolean rewritten = false;
-        for (int index = 0; index < op1.getInputs().size(); index++) {
-            AbstractLogicalOperator child = (AbstractLogicalOperator) op1.getInputs().get(index).getValue();
-            if (child.getOperatorTag() != LogicalOperatorTag.SUBPLAN) {
-                continue;
-            }
-
-            AbstractOperatorWithNestedPlans subplan = (AbstractOperatorWithNestedPlans) child;
-            Set<LogicalVariable> freeVars = new HashSet<LogicalVariable>();
-            OperatorPropertiesUtil.getFreeVariablesInSubplans(subplan, freeVars);
-            if (!freeVars.isEmpty()) {
-                /**
-                 * the subplan is correlated with the outer plan, other rules can deal with it
-                 */
-                continue;
-            }
-
-            /** get the input operator of the subplan operator */
-            ILogicalOperator subplanInput = subplan.getInputs().get(0).getValue();
-            AbstractLogicalOperator subplanInputOp = (AbstractLogicalOperator) subplanInput;
-
-            /** If the other join branch is a trivial plan, do not do the rewriting. */
-            if (subplanInputOp.getOperatorTag() == LogicalOperatorTag.EMPTYTUPLESOURCE) {
-                continue;
-            }
-
-            /** get all nested top operators */
-            List<ILogicalPlan> nestedPlans = subplan.getNestedPlans();
-            List<Mutable<ILogicalOperator>> nestedRoots = new ArrayList<Mutable<ILogicalOperator>>();
-            for (ILogicalPlan nestedPlan : nestedPlans) {
-                nestedRoots.addAll(nestedPlan.getRoots());
-            }
-            if (nestedRoots.size() == 0) {
-                /** there is no nested top operators */
-                continue;
-            }
-
-            /**
-             * Expends the input and roots into a DAG of nested loop joins.
-             * Though joins should be left-outer joins, a left-outer join with condition TRUE is equivalent to an inner join.
-             **/
-            Mutable<ILogicalExpression> expr = new MutableObject<ILogicalExpression>(ConstantExpression.TRUE);
-            Mutable<ILogicalOperator> nestedRootRef = nestedRoots.get(0);
-            ILogicalOperator join = new InnerJoinOperator(expr, new MutableObject<ILogicalOperator>(subplanInput),
-                    nestedRootRef);
-
-            /** rewrite the nested tuple source to be empty tuple source */
-            rewriteNestedTupleSource(nestedRootRef, context);
-
-            for (int i = 1; i < nestedRoots.size(); i++) {
-                join = new InnerJoinOperator(expr, new MutableObject<ILogicalOperator>(join), nestedRoots.get(i));
-            }
-            op1.getInputs().get(index).setValue(join);
-            context.computeAndSetTypeEnvironmentForOperator(join);
-            rewritten = true;
-        }
-        return rewritten;
-    }
-
-    /**
-     * rewrite NestedTupleSource operators to EmptyTupleSource operators
-     *
-     * @param nestedRootRef
-     */
-    private void rewriteNestedTupleSource(Mutable<ILogicalOperator> nestedRootRef, IOptimizationContext context)
-            throws AlgebricksException {
-        AbstractLogicalOperator nestedRoot = (AbstractLogicalOperator) nestedRootRef.getValue();
-        if (nestedRoot.getOperatorTag() == LogicalOperatorTag.NESTEDTUPLESOURCE) {
-            ILogicalOperator ets = new EmptyTupleSourceOperator();
-            nestedRootRef.setValue(ets);
-            context.computeAndSetTypeEnvironmentForOperator(ets);
-        }
-        List<Mutable<ILogicalOperator>> inputs = nestedRoot.getInputs();
-        for (Mutable<ILogicalOperator> input : inputs) {
-            rewriteNestedTupleSource(input, context);
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-asterixdb-hyracks/blob/7dd47992/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/PushSelectIntoJoinRule.java
----------------------------------------------------------------------
diff --git a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/PushSelectIntoJoinRule.java b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/PushSelectIntoJoinRule.java
index d6f1889..12e5ebe 100644
--- a/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/PushSelectIntoJoinRule.java
+++ b/algebricks/algebricks-rewriter/src/main/java/org/apache/hyracks/algebricks/rewriter/rules/PushSelectIntoJoinRule.java
@@ -28,7 +28,6 @@ import java.util.ListIterator;
 
 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.ILogicalExpression;
 import org.apache.hyracks.algebricks.core.algebra.base.ILogicalOperator;
@@ -64,6 +63,7 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
 
         List<ILogicalOperator> pushedOnLeft = new ArrayList<ILogicalOperator>();
         List<ILogicalOperator> pushedOnRight = new ArrayList<ILogicalOperator>();
+        List<ILogicalOperator> pushedOnEither = new ArrayList<ILogicalOperator>();
         LinkedList<ILogicalOperator> notPushedStack = new LinkedList<ILogicalOperator>();
         Collection<LogicalVariable> usedVars = new HashSet<LogicalVariable>();
         Collection<LogicalVariable> producedVars = new HashSet<LogicalVariable>();
@@ -107,7 +107,9 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
                 } else {
                     VariableUtilities.getUsedVariables(opIter, usedVars);
                     VariableUtilities.getProducedVariables(opIter, producedVars);
-                    if (joinLiveVarsLeft.containsAll(usedVars)) {
+                    if (usedVars.size() == 0) {
+                        pushedOnEither.add(opIter);
+                    } else if (joinLiveVarsLeft.containsAll(usedVars)) {
                         pushedOnLeft.add(opIter);
                         liveInOpsToPushLeft.addAll(producedVars);
                     } else if (joinLiveVarsRight.containsAll(usedVars)) {
@@ -149,6 +151,12 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
             return false;
         }
         if (needToPushOps) {
+            //We should push independent ops into the first branch that the selection depends on
+            if (intersectsBranch[0]) {
+                pushOps(pushedOnEither, joinBranchLeftRef, context);
+            } else {
+                pushOps(pushedOnEither, joinBranchRightRef, context);
+            }
             pushOps(pushedOnLeft, joinBranchLeftRef, context);
             pushOps(pushedOnRight, joinBranchRightRef, context);
         }
@@ -226,8 +234,8 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
             if (cond.getExpressionTag() == LogicalExpressionTag.FUNCTION_CALL) {
                 AbstractFunctionCallExpression fcond = (AbstractFunctionCallExpression) cond;
                 if (fcond.getFunctionIdentifier().equals(AlgebricksBuiltinFunctions.AND)) {
-                    AbstractFunctionCallExpression newCond = new ScalarFunctionCallExpression(context
-                            .getMetadataProvider().lookupFunction(AlgebricksBuiltinFunctions.AND));
+                    AbstractFunctionCallExpression newCond = new ScalarFunctionCallExpression(
+                            context.getMetadataProvider().lookupFunction(AlgebricksBuiltinFunctions.AND));
                     newCond.getArguments().add(select.getCondition());
                     newCond.getArguments().addAll(fcond.getArguments());
                     join.getCondition().setValue(newCond);
@@ -235,9 +243,9 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
                 }
             }
             if (!bAddedToConj) {
-                AbstractFunctionCallExpression newCond = new ScalarFunctionCallExpression(context.getMetadataProvider()
-                        .lookupFunction(AlgebricksBuiltinFunctions.AND), select.getCondition(),
-                        new MutableObject<ILogicalExpression>(join.getCondition().getValue()));
+                AbstractFunctionCallExpression newCond = new ScalarFunctionCallExpression(
+                        context.getMetadataProvider().lookupFunction(AlgebricksBuiltinFunctions.AND),
+                        select.getCondition(), new MutableObject<ILogicalExpression>(join.getCondition().getValue()));
                 join.getCondition().setValue(newCond);
             }
         }
@@ -255,7 +263,7 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
 
     /**
      * Whether the expression contains a not-null filtering
-     * 
+     *
      * @param expr
      * @return true if the expression contains a not-null filtering function call; false otherwise.
      */
@@ -288,7 +296,7 @@ public class PushSelectIntoJoinRule implements IAlgebraicRewriteRule {
 
     /**
      * Whether the expression contains a null filtering
-     * 
+     *
      * @param expr
      * @return true if the expression contains a null filtering function call; false otherwise.
      */


Mime
View raw message