@Override public IntermediateQuery optimize(IntermediateQuery query) { IntermediateQuery copy; IntermediateQuery updatedQuery = query; do { copy = updatedQuery; IntermediateQuery queryAfterUnionLift = liftUnionsAboveCn(updatedQuery); updatedQuery = flattenUnions(queryAfterUnionLift); } while (!IQSyntacticEquivalenceChecker.areEquivalent(updatedQuery, copy)); return updatedQuery; }
append(builder, parentInBuilder, updatedUnion, projectionAtom); sourceQuery.getChildren(sourceQueryNode).forEach(c -> liftCn( builder, bufferNode.clone(), liftCn( builder, mergeCns( bufferNode, (ConstructionNode) sourceQueryNode append(builder, parentInBuilder, bufferNode, projectionAtom); lift( builder, sourceQueryNode,
private void lift(IntermediateQueryBuilder builder, QueryNode bufferNode, Optional<QueryNode> parentInBuilder, IntermediateQuery sourceQuery, QueryNode sourceQueryNode, DistinctVariableOnlyDataAtom projectionAtom) { // Construction node: buffer it, and check the successor in the source query if (bufferNode instanceof ConstructionNode) { liftCn( builder, (ConstructionNode) bufferNode, parentInBuilder, sourceQuery, sourceQuery.getChildren(sourceQueryNode).iterator().next(), projectionAtom ); } else { // 'Flush' the buffer node: append it to the tree and go on with child(ren) as buffer(s) append(builder, parentInBuilder, bufferNode, projectionAtom); sourceQuery.getChildren(sourceQueryNode) .forEach(n -> lift( builder, n, Optional.of(bufferNode), sourceQuery, n, projectionAtom )); } }
/** * Lift substitutions and query modifiers, and get rid of resulting idle construction nodes. * Then flatten nested unions, and enforce non-nullability */ @Override public IntermediateQuery normalize(IntermediateQuery query) { IntermediateQuery queryAfterUnionNormalization; try { IntermediateQuery queryAfterBindingLift = bindingLifter.optimize(query); IntermediateQuery queryAfterCNodeCleaning = constructionNodeCleaner.optimize(queryAfterBindingLift); queryAfterUnionNormalization = mappingUnionNormalizer.optimize(queryAfterCNodeCleaning); } catch (EmptyQueryException e) { throw new DatalogConversionException("The query should not become empty"); } return noNullValueEnforcer.transform(queryAfterUnionNormalization); } }
private IntermediateQuery liftUnionsAboveCn(IntermediateQuery query) { if(query.getChildren(query.getRootNode()).isEmpty()){ return query; } IntermediateQueryBuilder builder = iqFactory.createIQBuilder( query.getDBMetadata(), query.getExecutorRegistry() ); lift(builder, query.getRootNode(), Optional.empty(), query, query.getRootNode(), query.getProjectionAtom()); return builder.build(); }