Browse Source

Initial work on trasnformer to common up some selectors

The call to the transformer currently has some problems on some example queries
so it is not enabled.  However the fixes are worth including in this release.

Signed-off-by: Gavin Halliday <gavin.halliday@lexisnexis.com>
Gavin Halliday 13 years ago
parent
commit
4d4a078ac7
5 changed files with 60 additions and 55 deletions
  1. 30 6
      ecl/hql/hqlpmap.cpp
  2. 1 29
      ecl/hql/hqltrans.ipp
  3. 1 0
      ecl/hqlcpp/hqlcpp.cpp
  4. 1 0
      ecl/hqlcpp/hqlcpp.ipp
  5. 27 20
      ecl/hqlcpp/hqlttcpp.cpp

+ 30 - 6
ecl/hql/hqlpmap.cpp

@@ -151,9 +151,21 @@ void replaceSelectors(HqlExprArray & out, IHqlExpression * expr, unsigned first,
     if (iChild == max)
         return;
 
-    HqlMapSelectorTransformer transformer(oldDataset, newDataset);
-    for (; iChild < max; iChild++)
-        out.append(*transformer.transformRoot(expr->queryChild(iChild)));
+    node_operator op = oldDataset->getOperator();
+    if (op == no_left || op == no_right)
+    {
+        NewSelectorReplacingTransformer transformer;
+        transformer.initSelectorMapping(oldDataset, newDataset);
+
+        for (; iChild < max; iChild++)
+            out.append(*transformer.transformRoot(expr->queryChild(iChild)));
+    }
+    else
+    {
+        HqlMapSelectorTransformer transformer(oldDataset, newDataset);
+        for (; iChild < max; iChild++)
+            out.append(*transformer.transformRoot(expr->queryChild(iChild)));
+    }
 }
 
 //---------------------------------------------------------------------------------------------------------------------
@@ -173,9 +185,21 @@ void replaceSelectors(HqlExprArray & exprs, unsigned first, IHqlExpression * old
     if (iChild == max)
         return;
 
-    HqlMapSelectorTransformer transformer(oldDataset, newDataset);
-    for (; iChild < max; iChild++)
-        exprs.replace(*transformer.transformRoot(&exprs.item(iChild)), iChild);
+    node_operator op = oldDataset->getOperator();
+    if (op == no_left || op == no_right)
+    {
+        NewSelectorReplacingTransformer transformer;
+        transformer.initSelectorMapping(oldDataset, newDataset);
+
+        for (; iChild < max; iChild++)
+            exprs.replace(*transformer.transformRoot(&exprs.item(iChild)), iChild);
+    }
+    else
+    {
+        HqlMapSelectorTransformer transformer(oldDataset, newDataset);
+        for (; iChild < max; iChild++)
+            exprs.replace(*transformer.transformRoot(&exprs.item(iChild)), iChild);
+    }
 }
 
 

+ 1 - 29
ecl/hql/hqltrans.ipp

@@ -424,7 +424,7 @@ protected:
 //---------------------------------------------------------------------------
 
 //This class is used for applying transformations to trees that have already been normalized, or
-//that need to assocaite extra information with the the expressions being transformed
+//that need to associate extra information with the the expressions being transformed
 //If the transformer inserts,swaps or hoists expressions then it should ensure that createTransformed()
 //processes the annotations and the body at the same time - otherwise they can become separated.
 class HQL_API NewHqlTransformer : public ANewHqlTransformer
@@ -945,34 +945,6 @@ public:
 };
 
 
-#if 0
-class HQL_API SelectorReplacingTransformer : public MergingHqlTransformer
-{
-public:
-    SelectorReplacingTransformer();
-
-    void initSelectorMapping(IHqlExpression * oldValue, IHqlExpression * newValue);
-
-    virtual IHqlExpression * createTransformed(IHqlExpression * expr);
-
-    inline bool foundAmbiguity() const { return introducesAmbiguity; }
-
-protected:
-    void updateMapping();
-    virtual void pushChildContext(IHqlExpression * expr, IHqlExpression * transformed);
-
-protected:
-    OwnedHqlExpr oldSelector;
-    OwnedHqlExpr newSelector;
-    OwnedHqlExpr oldDataset;
-    OwnedHqlExpr newDataset;
-    bool isHidden;
-    bool introducesAmbiguity;
-    IHqlExpression * savedNewDataset;
-};
-#endif
-
-
 class HQL_API NewSelectorReplacingInfo : public NewTransformInfo
 {
 public:

+ 1 - 0
ecl/hqlcpp/hqlcpp.cpp

@@ -1684,6 +1684,7 @@ void HqlCppTranslator::cacheOptions()
         DebugOption(options.shuffleLocalJoinConditions,"shuffleLocalJoinConditions",false),
         DebugOption(options.projectNestedTables,"projectNestedTables",true),
         DebugOption(options.showSeqInGraph,"showSeqInGraph",false),  // For tracking down why projects are not commoned up
+        DebugOption(options.normalizeSelectorSequence,"normalizeSelectorSequence",false),  // For tracking down why projects are not commoned up
     };
 
     //get options values from workunit

+ 1 - 0
ecl/hqlcpp/hqlcpp.ipp

@@ -713,6 +713,7 @@ struct HqlCppOptions
     bool                shuffleLocalJoinConditions;
     bool                projectNestedTables;
     bool                showSeqInGraph;
+    bool                normalizeSelectorSequence;
 };
 
 //Any information gathered while processing the query should be moved into here, rather than cluttering up the translator class

+ 27 - 20
ecl/hqlcpp/hqlttcpp.cpp

@@ -9393,6 +9393,7 @@ void LeftRightTransformer::analyseExpr(IHqlExpression * _expr)
     NewHqlTransformer::analyseExpr(body);
     if (pass == 0)
     {
+        //First pass gathers a list of selectors that are potentially ambiguous if the sequence was removed
         IHqlExpression * left = NULL;
         IHqlExpression * right = NULL;
         switch (getChildDatasetType(body))
@@ -9434,13 +9435,25 @@ void LeftRightTransformer::analyseExpr(IHqlExpression * _expr)
     }
     else
     {
+        //Second pass - for each expression, gather a list of selectors that would actually be ambiguous.
         LeftRightTransformInfo * extra = queryExtra(body);
-        if (extra->rawLeft)
+        IHqlExpression * rawLeft = extra->rawLeft;
+        IHqlExpression * rawRight = extra->rawRight;
+
+        //If LEFT is potentially ambiguous, then add it to the list of selectors used by this expression
+        if (rawLeft)
         {
-            LeftRightTransformInfo * leftExtra = queryExtra(extra->rawLeft);
+            LeftRightTransformInfo * leftExtra = queryExtra(rawLeft);
             if (leftExtra->shared)
                 extra->add(leftExtra->shared);
         }
+        //Ditto for right
+        if (rawRight)
+        {
+            LeftRightTransformInfo * rightExtra = queryExtra(rawRight);
+            if (rightExtra->shared)
+                extra->add(rightExtra->shared);
+        }
 
         switch (body->getOperator())
         {
@@ -9466,32 +9479,27 @@ void LeftRightTransformer::analyseExpr(IHqlExpression * _expr)
             }
         }
 
-        IHqlExpression * left = extra->rawLeft;
-        IHqlExpression * right = extra->rawRight;
         ForEachChild(i, body)
         {
             IHqlExpression * cur = body->queryChild(i);
             LeftRightTransformInfo * childExtra = queryExtra(cur->queryBody());
             //If this is one of the arguments to an operation which has an active top dataset,
             //check to see if any of the contained expressions reference this item
-            if ((i != 0) && (left || right))
+            if ((i != 0) && rawLeft)
             {
-                if (left)
+                SharedTableInfo * matchLeft = childExtra->uses(rawLeft);
+                SharedTableInfo * matchRight = rawRight ? childExtra->uses(rawRight) : NULL;
+                if (matchLeft || matchRight)
                 {
-                    SharedTableInfo * matchLeft = childExtra->uses(left);
-                    SharedTableInfo * matchRight = right ? childExtra->uses(right) : NULL;
-                    if (matchLeft || matchRight)
+                    unsigned leftDepth = matchLeft ? matchLeft->depth : 0;
+                    unsigned rightDepth = matchRight ? matchRight->depth : 0;
+                    unsigned depth = leftDepth > rightDepth ? leftDepth : rightDepth;
+                    SharedTableInfo * nested = createAmbiguityInfo(rawLeft, depth+1);
+                    extra->addAmbiguity(nested);
+                    if (rawRight)
                     {
-                        unsigned leftDepth = matchLeft ? matchLeft->depth : 0;
-                        unsigned rightDepth = matchRight ? matchRight->depth : 0;
-                        unsigned depth = leftDepth > rightDepth ? leftDepth : rightDepth;
-                        SharedTableInfo * nested = createAmbiguityInfo(left, depth+1);
+                        SharedTableInfo * nested = createAmbiguityInfo(rawRight, depth+1);
                         extra->addAmbiguity(nested);
-                        if (matchRight)
-                        {
-                            SharedTableInfo * nested = createAmbiguityInfo(right, depth+1);
-                            extra->addAmbiguity(nested);
-                        }
                     }
                 }
             }
@@ -12306,8 +12314,8 @@ bool HqlCppTranslator::transformGraphForGeneration(IHqlExpression * query, Workf
     checkNormalized(workflow);
     DEBUG_TIMER("EclServer: tree transform: stored results", msTick()-time4);
 
-#ifdef NORMALIZE_SELSEQ
 #ifdef USE_SELSEQ_UID
+    if (options.normalizeSelectorSequence)
     {
         unsigned time = msTick();
         ForEachItemIn(i, workflow)
@@ -12319,7 +12327,6 @@ bool HqlCppTranslator::transformGraphForGeneration(IHqlExpression * query, Workf
         //traceExpressions("after implicit alias", workflow);
     }
 #endif
-#endif
 
     if (queryOptions().createImplicitAliases)
     {