mirror of https://gitee.com/bigwinds/arangodb
Started to implement functions to find indexes for each Condition sub part
This commit is contained in:
parent
1e5b246b6b
commit
f1b0afd9a6
|
@ -134,7 +134,36 @@ void Condition::andCombine (AstNode const* node) {
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief locate indices for each condition
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
void Condition::findIndices() {
|
||||
|
||||
void Condition::findIndices (EnumerateCollectionNode const* node) {
|
||||
// We can only start after DNF transform
|
||||
Variable const* reference = node->outVariable();
|
||||
TRI_ASSERT(_root->type == NODE_TYPE_OPERATOR_NARY_OR);
|
||||
for (size_t i = 0; i < _root->numMembers(); ++i) {
|
||||
findIndexForAndNode(_root->getMember(i), reference, node);
|
||||
}
|
||||
}
|
||||
|
||||
void Condition::findIndexForAndNode (AstNode const* node, Variable const* reference, EnumerateCollectionNode const* colNode) {
|
||||
// We are not iterating through the DNF properly
|
||||
TRI_ASSERT(node->type == NODE_TYPE_OPERATOR_NARY_AND);
|
||||
std::unordered_set<std::string> attributes;
|
||||
for (size_t i = 0; i < node->numMembers(); ++i) {
|
||||
auto compareNode = node->getMember(i);
|
||||
switch (compareNode->type) {
|
||||
default:
|
||||
for (size_t j = 0; j < compareNode->numMembers(); ++j) {
|
||||
auto fuxxNode = compareNode->getMember(j);
|
||||
if (fuxxNode->type == NODE_TYPE_ATTRIBUTE_ACCESS) {
|
||||
// if (static_cast<Variable const*>(fuxxNode->getMember(0)->getData()) == reference) {
|
||||
if (fuxxNode->getMember(0)->getData() == reference) {
|
||||
attributes.emplace(fuxxNode->getStringValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// std::string node->getStringValue()
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -148,181 +177,6 @@ void Condition::normalize (ExecutionPlan* plan) {
|
|||
return;
|
||||
}
|
||||
|
||||
std::function<AstNode*(AstNode*)> transformNode = [this, &transformNode] (AstNode* node) -> AstNode* {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_BINARY_AND ||
|
||||
node->type == NODE_TYPE_OPERATOR_BINARY_OR) {
|
||||
// convert binary AND/OR into n-ary AND/OR
|
||||
auto lhs = node->getMember(0);
|
||||
auto rhs = node->getMember(1);
|
||||
node = _ast->createNodeBinaryOperator(Ast::NaryOperatorType(node->type), lhs, rhs);
|
||||
}
|
||||
|
||||
TRI_ASSERT(node->type != NODE_TYPE_OPERATOR_BINARY_AND &&
|
||||
node->type != NODE_TYPE_OPERATOR_BINARY_OR);
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_NARY_AND) {
|
||||
// first recurse into subnodes
|
||||
node->changeMember(0, transformNode(node->getMember(0)));
|
||||
node->changeMember(1, transformNode(node->getMember(1)));
|
||||
|
||||
auto lhs = node->getMember(0);
|
||||
auto rhs = node->getMember(1);
|
||||
|
||||
if (lhs->type == NODE_TYPE_OPERATOR_NARY_OR &&
|
||||
rhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(0), rhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(0), rhs->getMember(1)));
|
||||
auto or1 = _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
|
||||
auto and3 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(1), rhs->getMember(0)));
|
||||
auto and4 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(1), rhs->getMember(1)));
|
||||
auto or2 = _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and3, and4);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, or1, or2);
|
||||
}
|
||||
else if (lhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, rhs, lhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, rhs, lhs->getMember(1)));
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
}
|
||||
else if (rhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs, rhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs, rhs->getMember(1)));
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
}
|
||||
}
|
||||
else if (node->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
// recurse into subnodes
|
||||
node->changeMember(0, transformNode(node->getMember(0)));
|
||||
node->changeMember(1, transformNode(node->getMember(1)));
|
||||
}
|
||||
else if (node->type == NODE_TYPE_OPERATOR_UNARY_NOT) {
|
||||
// push down logical negations
|
||||
auto sub = node->getMemberUnchecked(0);
|
||||
|
||||
if (sub->type == NODE_TYPE_OPERATOR_NARY_AND ||
|
||||
sub->type == NODE_TYPE_OPERATOR_BINARY_AND) {
|
||||
// ! (a && b) => (! a) || (! b)
|
||||
auto neg1 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(0)));
|
||||
auto neg2 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(1)));
|
||||
|
||||
neg1 = _ast->optimizeNotExpression(neg1);
|
||||
neg2 = _ast->optimizeNotExpression(neg2);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, neg1, neg2);
|
||||
}
|
||||
else if (sub->type == NODE_TYPE_OPERATOR_NARY_OR ||
|
||||
sub->type == NODE_TYPE_OPERATOR_BINARY_OR) {
|
||||
// ! (a || b) => (! a) && (! b)
|
||||
auto neg1 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(0)));
|
||||
auto neg2 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(1)));
|
||||
|
||||
neg1 = _ast->optimizeNotExpression(neg1);
|
||||
neg2 = _ast->optimizeNotExpression(neg2);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, neg1, neg2);
|
||||
}
|
||||
|
||||
node->changeMember(0, transformNode(sub));
|
||||
return node;
|
||||
}
|
||||
|
||||
return node;
|
||||
};
|
||||
|
||||
// collapse function.
|
||||
// this will collapse nested logical AND/OR nodes
|
||||
std::function<AstNode*(AstNode*)> collapseNesting = [this, &collapseNesting] (AstNode* node) -> AstNode* {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_NARY_AND ||
|
||||
node->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
// first recurse into subnodes
|
||||
size_t const n = node->numMembers();
|
||||
|
||||
for (size_t i = 0; i < n; ++i) {
|
||||
auto sub = collapseNesting(node->getMemberUnchecked(i));
|
||||
|
||||
if (sub->type == node->type) {
|
||||
// sub-node has the same type as parent node
|
||||
// now merge the sub-nodes of the sub-node into the parent node
|
||||
size_t const subNumMembers = sub->numMembers();
|
||||
|
||||
for (size_t j = 0; j < subNumMembers; ++j) {
|
||||
node->addMember(sub->getMemberUnchecked(j));
|
||||
}
|
||||
// invalidate the child node which we just expanded
|
||||
node->changeMember(i, _ast->createNodeNop());
|
||||
}
|
||||
else {
|
||||
// different type
|
||||
node->changeMember(i, sub);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return node;
|
||||
};
|
||||
|
||||
// finally create a top-level OR node if it does not already exist, and make sure that all second
|
||||
// level nodes are AND nodes
|
||||
// additionally, this processing step will remove all NOP nodes
|
||||
std::function<AstNode*(AstNode*, int)> fixRoot = [this, &fixRoot] (AstNode* node, int level) -> AstNode* {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
AstNodeType type;
|
||||
|
||||
if (level == 0) {
|
||||
type = NODE_TYPE_OPERATOR_NARY_OR;
|
||||
}
|
||||
else {
|
||||
type = NODE_TYPE_OPERATOR_NARY_AND;
|
||||
}
|
||||
// check if first-level node is an OR node
|
||||
if (node->type != type) {
|
||||
// create new root node
|
||||
node = _ast->createNodeNaryOperator(type, node);
|
||||
}
|
||||
|
||||
size_t const n = node->numMembers();
|
||||
size_t j = 0;
|
||||
|
||||
for (size_t i = 0; i < n; ++i) {
|
||||
auto sub = node->getMemberUnchecked(i);
|
||||
|
||||
if (sub->type == NODE_TYPE_NOP) {
|
||||
// ignore this node
|
||||
continue;
|
||||
}
|
||||
|
||||
if (level == 0) {
|
||||
// recurse into next level
|
||||
node->changeMember(j, fixRoot(sub, level + 1));
|
||||
}
|
||||
else if (i != j) {
|
||||
node->changeMember(j, sub);
|
||||
}
|
||||
++j;
|
||||
}
|
||||
|
||||
if (j != n) {
|
||||
// adjust number of members (because of the NOP nodes removes)
|
||||
node->reduceMembers(j);
|
||||
}
|
||||
|
||||
return node;
|
||||
};
|
||||
|
||||
_root = transformNode(_root);
|
||||
_root = collapseNesting(_root);
|
||||
_root = fixRoot(_root, 0);
|
||||
|
@ -332,7 +186,6 @@ void Condition::normalize (ExecutionPlan* plan) {
|
|||
std::cout << "\n";
|
||||
dump();
|
||||
std::cout << "\n";
|
||||
|
||||
_isNormalized = true;
|
||||
}
|
||||
|
||||
|
@ -403,6 +256,7 @@ ConditionPart::ConditionPartCompareResult ConditionPart::ResultsTable[3][7][7] =
|
|||
{DISJOINT, DISJOINT, DISJOINT, DISJOINT, DISJOINT, DISJOINT, DISJOINT}
|
||||
}
|
||||
};
|
||||
|
||||
void Condition::optimize (ExecutionPlan* plan) {
|
||||
|
||||
// normalize();
|
||||
|
@ -558,7 +412,7 @@ void Condition::optimize (ExecutionPlan* plan) {
|
|||
} // cross compare sub-and-nodes
|
||||
} // foreach sub-and-node
|
||||
fastForwardToNextOrItem:
|
||||
true;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -587,6 +441,9 @@ void Condition::dump () const {
|
|||
else if (node->type == NODE_TYPE_ATTRIBUTE_ACCESS) {
|
||||
std::cout << " (attribute " << node->getStringValue() << ")";
|
||||
}
|
||||
else if (node->type == NODE_TYPE_REFERENCE) {
|
||||
std::cout << " (name " << node->getStringValue() << ")";
|
||||
}
|
||||
|
||||
std::cout << "\n";
|
||||
for (size_t i = 0; i < node->numMembers(); ++i) {
|
||||
|
@ -597,6 +454,175 @@ void Condition::dump () const {
|
|||
dumpNode(_root, 0);
|
||||
}
|
||||
|
||||
AstNode* Condition::transformNode (AstNode* node) {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_BINARY_AND ||
|
||||
node->type == NODE_TYPE_OPERATOR_BINARY_OR) {
|
||||
// convert binary AND/OR into n-ary AND/OR
|
||||
auto lhs = node->getMember(0);
|
||||
auto rhs = node->getMember(1);
|
||||
node = _ast->createNodeBinaryOperator(Ast::NaryOperatorType(node->type), lhs, rhs);
|
||||
}
|
||||
|
||||
TRI_ASSERT(node->type != NODE_TYPE_OPERATOR_BINARY_AND &&
|
||||
node->type != NODE_TYPE_OPERATOR_BINARY_OR);
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_NARY_AND) {
|
||||
// first recurse into subnodes
|
||||
node->changeMember(0, transformNode(node->getMember(0)));
|
||||
node->changeMember(1, transformNode(node->getMember(1)));
|
||||
|
||||
auto lhs = node->getMember(0);
|
||||
auto rhs = node->getMember(1);
|
||||
|
||||
if (lhs->type == NODE_TYPE_OPERATOR_NARY_OR &&
|
||||
rhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(0), rhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(0), rhs->getMember(1)));
|
||||
auto or1 = _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
|
||||
auto and3 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(1), rhs->getMember(0)));
|
||||
auto and4 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs->getMember(1), rhs->getMember(1)));
|
||||
auto or2 = _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and3, and4);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, or1, or2);
|
||||
}
|
||||
else if (lhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, rhs, lhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, rhs, lhs->getMember(1)));
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
}
|
||||
else if (rhs->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
auto and1 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs, rhs->getMember(0)));
|
||||
auto and2 = transformNode(_ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, lhs, rhs->getMember(1)));
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, and1, and2);
|
||||
}
|
||||
}
|
||||
else if (node->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
// recurse into subnodes
|
||||
node->changeMember(0, transformNode(node->getMember(0)));
|
||||
node->changeMember(1, transformNode(node->getMember(1)));
|
||||
}
|
||||
else if (node->type == NODE_TYPE_OPERATOR_UNARY_NOT) {
|
||||
// push down logical negations
|
||||
auto sub = node->getMemberUnchecked(0);
|
||||
|
||||
if (sub->type == NODE_TYPE_OPERATOR_NARY_AND ||
|
||||
sub->type == NODE_TYPE_OPERATOR_BINARY_AND) {
|
||||
// ! (a && b) => (! a) || (! b)
|
||||
auto neg1 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(0)));
|
||||
auto neg2 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(1)));
|
||||
|
||||
neg1 = _ast->optimizeNotExpression(neg1);
|
||||
neg2 = _ast->optimizeNotExpression(neg2);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_OR, neg1, neg2);
|
||||
}
|
||||
else if (sub->type == NODE_TYPE_OPERATOR_NARY_OR ||
|
||||
sub->type == NODE_TYPE_OPERATOR_BINARY_OR) {
|
||||
// ! (a || b) => (! a) && (! b)
|
||||
auto neg1 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(0)));
|
||||
auto neg2 = transformNode(_ast->createNodeUnaryOperator(NODE_TYPE_OPERATOR_UNARY_NOT, sub->getMember(1)));
|
||||
|
||||
neg1 = _ast->optimizeNotExpression(neg1);
|
||||
neg2 = _ast->optimizeNotExpression(neg2);
|
||||
|
||||
return _ast->createNodeBinaryOperator(NODE_TYPE_OPERATOR_NARY_AND, neg1, neg2);
|
||||
}
|
||||
|
||||
node->changeMember(0, transformNode(sub));
|
||||
return node;
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
AstNode* Condition::collapseNesting (AstNode* node) {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (node->type == NODE_TYPE_OPERATOR_NARY_AND ||
|
||||
node->type == NODE_TYPE_OPERATOR_NARY_OR) {
|
||||
// first recurse into subnodes
|
||||
size_t const n = node->numMembers();
|
||||
|
||||
for (size_t i = 0; i < n; ++i) {
|
||||
auto sub = collapseNesting(node->getMemberUnchecked(i));
|
||||
|
||||
if (sub->type == node->type) {
|
||||
// sub-node has the same type as parent node
|
||||
// now merge the sub-nodes of the sub-node into the parent node
|
||||
size_t const subNumMembers = sub->numMembers();
|
||||
|
||||
for (size_t j = 0; j < subNumMembers; ++j) {
|
||||
node->addMember(sub->getMemberUnchecked(j));
|
||||
}
|
||||
// invalidate the child node which we just expanded
|
||||
node->changeMember(i, _ast->createNodeNop());
|
||||
}
|
||||
else {
|
||||
// different type
|
||||
node->changeMember(i, sub);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
AstNode* Condition::fixRoot (AstNode* node, int level) {
|
||||
if (node == nullptr) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
AstNodeType type;
|
||||
|
||||
if (level == 0) {
|
||||
type = NODE_TYPE_OPERATOR_NARY_OR;
|
||||
}
|
||||
else {
|
||||
type = NODE_TYPE_OPERATOR_NARY_AND;
|
||||
}
|
||||
// check if first-level node is an OR node
|
||||
if (node->type != type) {
|
||||
// create new root node
|
||||
node = _ast->createNodeNaryOperator(type, node);
|
||||
}
|
||||
|
||||
size_t const n = node->numMembers();
|
||||
size_t j = 0;
|
||||
|
||||
for (size_t i = 0; i < n; ++i) {
|
||||
auto sub = node->getMemberUnchecked(i);
|
||||
|
||||
if (sub->type == NODE_TYPE_NOP) {
|
||||
// ignore this node
|
||||
continue;
|
||||
}
|
||||
|
||||
if (level == 0) {
|
||||
// recurse into next level
|
||||
node->changeMember(j, fixRoot(sub, level + 1));
|
||||
}
|
||||
else if (i != j) {
|
||||
node->changeMember(j, sub);
|
||||
}
|
||||
++j;
|
||||
}
|
||||
|
||||
if (j != n) {
|
||||
// adjust number of members (because of the NOP nodes removes)
|
||||
node->reduceMembers(j);
|
||||
}
|
||||
|
||||
return node;
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// --SECTION-- END-OF-FILE
|
||||
|
|
|
@ -32,6 +32,7 @@
|
|||
|
||||
#include "Basics/Common.h"
|
||||
#include "Aql/AstNode.h"
|
||||
#include "Aql/ExecutionNode.h"
|
||||
|
||||
namespace triagens {
|
||||
namespace aql {
|
||||
|
@ -171,7 +172,7 @@ namespace triagens {
|
|||
/// @brief locate indices which can be used for conditions
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void findIndices ();
|
||||
void findIndices (EnumerateCollectionNode const*);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief dump the condition
|
||||
|
@ -180,6 +181,37 @@ namespace triagens {
|
|||
void dump () const;
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// --SECTION-- private methods
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
private:
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief Transforms the AstNode
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
AstNode* transformNode (AstNode*);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief Collapses nested logical AND/OR nodes
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
AstNode* collapseNesting (AstNode*);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief Creates a top-level OR node if it does not already exist, and make sure that all second
|
||||
/// level nodes are AND nodes. Additionally, this processing step will
|
||||
/// remove all NOP nodes.
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
AstNode* fixRoot (AstNode*, int);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief Finds all indexes that can match this single node
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void findIndexForAndNode (AstNode const*, Variable const*, EnumerateCollectionNode const*);
|
||||
// -----------------------------------------------------------------------------
|
||||
// --SECTION-- private variables
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
|
|
|
@ -2119,6 +2119,7 @@ class ConditionFinder : public WalkerWorker<ExecutionNode> {
|
|||
// auto node = static_cast<EnumerateCollectionNode*>(en);
|
||||
// auto var = node->getVariablesSetHere()[0]; // should only be 1
|
||||
_condition->normalize(_plan);
|
||||
_condition->findIndices(static_cast<EnumerateCollectionNode const*>(en));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue