/**
Copyright (C) SYSTAP, LLC DBA Blazegraph 2006-2016. All rights reserved.
Contact:
SYSTAP, LLC DBA Blazegraph
2501 Calvert ST NW #106
Washington, DC 20008
licenses@blazegraph.com
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; version 2 of the License.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
/*
* Created on Aug 29, 2011
*/
package com.bigdata.rdf.sparql.ast.optimizers;
import org.openrdf.model.impl.URIImpl;
import org.openrdf.model.vocabulary.RDF;
import com.bigdata.bop.IBindingSet;
import com.bigdata.rdf.internal.IV;
import com.bigdata.rdf.sparql.ast.ConstantNode;
import com.bigdata.rdf.sparql.ast.FilterNode;
import com.bigdata.rdf.sparql.ast.FunctionNode;
import com.bigdata.rdf.sparql.ast.FunctionRegistry;
import com.bigdata.rdf.sparql.ast.IQueryNode;
import com.bigdata.rdf.sparql.ast.JoinGroupNode;
import com.bigdata.rdf.sparql.ast.ProjectionNode;
import com.bigdata.rdf.sparql.ast.QueryNodeWithBindingSet;
import com.bigdata.rdf.sparql.ast.QueryRoot;
import com.bigdata.rdf.sparql.ast.QueryType;
import com.bigdata.rdf.sparql.ast.StatementPatternNode;
import com.bigdata.rdf.sparql.ast.UnionNode;
import com.bigdata.rdf.sparql.ast.ValueExpressionNode;
import com.bigdata.rdf.sparql.ast.VarNode;
/**
* Test suite for {@link ASTUnionFiltersOptimizer}.
*
* @author <a href="mailto:mrpersonick@users.sourceforge.net">Mike Personick</a>
* @version $Id: TestASTEmptyGroupOptimizer.java 5302 2011-10-07 14:28:03Z
* thompsonbry $
*/
public class TestASTUnionFiltersOptimizer extends AbstractOptimizerTestCase {
/**
*
*/
public TestASTUnionFiltersOptimizer() {
}
/**
* @param name
*/
public TestASTUnionFiltersOptimizer(String name) {
super(name);
}
/**
* https://sourceforge.net/apps/trac/bigdata/ticket/416
*/
@SuppressWarnings("rawtypes")
public void test_ticket416() throws Exception {
/*
* Note: DO NOT share structures in this test!!!!
*/
final IBindingSet[] bsets = new IBindingSet[]{};
final IV type = makeIV(RDF.TYPE);
final IV a = makeIV(new URIImpl("http://example/a"));
final IV t1 = makeIV(new URIImpl("http://example/t1"));
final IV t2 = makeIV(new URIImpl("http://example/t2"));
// The source AST.
final QueryRoot given = new QueryRoot(QueryType.SELECT);
{
final ProjectionNode projection = new ProjectionNode();
projection.addProjectionVar(new VarNode("s"));
projection.addProjectionVar(new VarNode("p"));
projection.addProjectionVar(new VarNode("r"));
projection.addProjectionVar(new VarNode("l"));
projection.setDistinct(true);
final UnionNode union = new UnionNode(); // outer
final JoinGroupNode left = new JoinGroupNode();
left.addChild(new StatementPatternNode(
new VarNode("s"),
new ConstantNode(type),
new ConstantNode(a)));
left.addChild(new StatementPatternNode(
new VarNode("s"),
new VarNode("p"),
new VarNode("r")));
left.addChild(new StatementPatternNode(
new VarNode("r"),
new ConstantNode(type),
new VarNode("type")));
final JoinGroupNode right = new JoinGroupNode();
right.addChild(new StatementPatternNode(
new VarNode("s"),
new ConstantNode(type),
new ConstantNode(a)));
right.addChild(new StatementPatternNode(
new VarNode("l"),
new VarNode("p"),
new VarNode("s")));
right.addChild(new StatementPatternNode(
new VarNode("l"),
new ConstantNode(type),
new VarNode("type")));
union.addChild(left);
union.addChild(right);
final JoinGroupNode where = new JoinGroupNode();
where.addChild(union);
where.addChild(new FilterNode(new FilterNode(new FunctionNode(
FunctionRegistry.OR,
null/*scalarValues*/,
new ValueExpressionNode[] {
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t1)
}),
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t2)
})
}))));
given.setProjection(projection);
given.setWhereClause(where);
}
// The expected AST after the rewrite.
final QueryRoot expected = new QueryRoot(QueryType.SELECT);
{
final ProjectionNode projection = new ProjectionNode();
projection.addProjectionVar(new VarNode("s"));
projection.addProjectionVar(new VarNode("p"));
projection.addProjectionVar(new VarNode("r"));
projection.addProjectionVar(new VarNode("l"));
projection.setDistinct(true);
final UnionNode union = new UnionNode(); // outer
final JoinGroupNode left = new JoinGroupNode();
left.addChild(new StatementPatternNode(
new VarNode("s"),
new ConstantNode(type),
new ConstantNode(a)));
left.addChild(new StatementPatternNode(
new VarNode("s"),
new VarNode("p"),
new VarNode("r")));
left.addChild(new StatementPatternNode(
new VarNode("r"),
new ConstantNode(type),
new VarNode("type")));
left.addChild(new FilterNode(new FunctionNode(
FunctionRegistry.OR,
null/*scalarValues*/,
new ValueExpressionNode[] {
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t1)
}),
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t2)
})
})));
final JoinGroupNode right = new JoinGroupNode();
right.addChild(new StatementPatternNode(
new VarNode("s"),
new ConstantNode(type),
new ConstantNode(a)));
right.addChild(new StatementPatternNode(
new VarNode("l"),
new VarNode("p"),
new VarNode("s")));
right.addChild(new StatementPatternNode(
new VarNode("l"),
new ConstantNode(type),
new VarNode("type")));
right.addChild(new FilterNode(new FunctionNode(
FunctionRegistry.OR,
null/*scalarValues*/,
new ValueExpressionNode[] {
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t1)
}),
new FunctionNode(
FunctionRegistry.SAME_TERM,
null/*scalarValues*/,
new ValueExpressionNode[] {
new VarNode("type"),
new ConstantNode(t2)
})
})));
union.addChild(left);
union.addChild(right);
expected.setProjection(projection);
expected.setWhereClause(union);
}
final IASTOptimizer opt1 = new ASTUnionFiltersOptimizer();
final IASTOptimizer opt2 = new ASTEmptyGroupOptimizer();
final IQueryNode actual = opt2.optimize(
null/* AST2BOpContext */,
new QueryNodeWithBindingSet(
opt1.optimize(null/* AST2BOpContext */, new QueryNodeWithBindingSet(given, bsets)).getQueryNode(),
bsets)
).getQueryNode();
assertSameAST(expected, actual);
}
@Override
IASTOptimizer newOptimizer() {
return new ASTOptimizerList(new ASTUnionFiltersOptimizer(), new ASTBottomUpOptimizer());
}
public void test_ticket767_case2() {
new Helper(){{
given = select( varNode(w),
where ( joinGroupNode(
unionNode(
joinGroupNode(
statementPatternNode(constantNode(a),constantNode(b),varNode(w))
),
joinGroupNode()
),
filter(bound(varNode(w)))
) ) );
expected = select( varNode(w),
where (joinGroupNode(
unionNode(
joinGroupNode(
statementPatternNode(constantNode(a),constantNode(b),varNode(w)),
filter(bound(varNode(w)))),
joinGroupNode(filter(knownUnbound(varNode(w))))
)
) ) );
}}.testWhileIgnoringExplainHints();
}
/**
* This optimizer cannot help in this case.
*/
public void test_ticket905() {
new Helper(){
QueryRoot unchanged() {
return select( varNode(w),
where ( joinGroupNode(
statementPatternNode(constantNode(a),constantNode(b),varNode(w)),
filter(bound(varNode(w))),
statementPatternNode(varNode(x),constantNode(b),varNode(w)),
unionNode(
joinGroupNode(
bind(constantNode(a), varNode(x) )
),
joinGroupNode(
bind(constantNode(b), varNode(x) )
)
)
) ) );
}
{
given = unchanged();
expected = unchanged();
}}.test();
}
}