use of org.apache.calcite.rel.logical.LogicalTableFunctionScan in project calcite by apache.
the class EnumerableTableFunctionScanRule method convert.
@Override
public RelNode convert(RelNode rel) {
final RelTraitSet traitSet = rel.getTraitSet().replace(EnumerableConvention.INSTANCE);
LogicalTableFunctionScan tbl = (LogicalTableFunctionScan) rel;
return new EnumerableTableFunctionScan(rel.getCluster(), traitSet, tbl.getInputs(), tbl.getElementType(), tbl.getRowType(), tbl.getCall(), tbl.getColumnMappings());
}
use of org.apache.calcite.rel.logical.LogicalTableFunctionScan in project flink by apache.
the class JoinTableFunctionScanToCorrelateRule method onMatch.
@Override
public void onMatch(RelOptRuleCall call) {
LogicalJoin join = call.rel(0);
RelNode leftInput = call.rel(1);
LogicalTableFunctionScan logicalTableFunctionScan = call.rel(2);
RelNode correlate = call.builder().push(leftInput).push(logicalTableFunctionScan).correlate(join.getJoinType(), join.getCluster().createCorrel()).build();
call.transformTo(correlate);
}
use of org.apache.calcite.rel.logical.LogicalTableFunctionScan in project calcite by apache.
the class FilterTableFunctionTransposeRule method onMatch.
// ~ Methods ----------------------------------------------------------------
// implement RelOptRule
public void onMatch(RelOptRuleCall call) {
LogicalFilter filter = call.rel(0);
LogicalTableFunctionScan funcRel = call.rel(1);
Set<RelColumnMapping> columnMappings = funcRel.getColumnMappings();
if (columnMappings == null || columnMappings.isEmpty()) {
// possible.
return;
}
List<RelNode> funcInputs = funcRel.getInputs();
if (funcInputs.size() != 1) {
// offsetting field indices, similar to join
return;
}
// TODO: support mappings other than 1-to-1
if (funcRel.getRowType().getFieldCount() != funcInputs.get(0).getRowType().getFieldCount()) {
return;
}
for (RelColumnMapping mapping : columnMappings) {
if (mapping.iInputColumn != mapping.iOutputColumn) {
return;
}
if (mapping.derived) {
return;
}
}
final List<RelNode> newFuncInputs = new ArrayList<RelNode>();
final RelOptCluster cluster = funcRel.getCluster();
final RexNode condition = filter.getCondition();
// create filters on top of each func input, modifying the filter
// condition to reference the child instead
RexBuilder rexBuilder = filter.getCluster().getRexBuilder();
List<RelDataTypeField> origFields = funcRel.getRowType().getFieldList();
// TODO: these need to be non-zero once we
// support arbitrary mappings
int[] adjustments = new int[origFields.size()];
for (RelNode funcInput : funcInputs) {
RexNode newCondition = condition.accept(new RelOptUtil.RexInputConverter(rexBuilder, origFields, funcInput.getRowType().getFieldList(), adjustments));
newFuncInputs.add(LogicalFilter.create(funcInput, newCondition));
}
// create a new UDX whose children are the filters created above
LogicalTableFunctionScan newFuncRel = LogicalTableFunctionScan.create(cluster, newFuncInputs, funcRel.getCall(), funcRel.getElementType(), funcRel.getRowType(), columnMappings);
call.transformTo(newFuncRel);
}
use of org.apache.calcite.rel.logical.LogicalTableFunctionScan in project flink by apache.
the class ProjectWindowTableFunctionTransposeRule method onMatch.
@Override
public void onMatch(RelOptRuleCall call) {
LogicalProject project = call.rel(0);
LogicalTableFunctionScan scan = call.rel(1);
RelNode scanInput = scan.getInput(0);
TimeAttributeWindowingStrategy windowingStrategy = WindowUtil.convertToWindowingStrategy((RexCall) scan.getCall(), scanInput.getRowType());
// 1. get fields to push down
ImmutableBitSet projectFields = RelOptUtil.InputFinder.bits(project.getProjects(), null);
int scanInputFieldCount = scanInput.getRowType().getFieldCount();
ImmutableBitSet toPushFields = ImmutableBitSet.range(0, scanInputFieldCount).intersect(projectFields).set(windowingStrategy.getTimeAttributeIndex());
if (toPushFields.cardinality() == scanInputFieldCount) {
return;
}
// 2. create new input of window table function scan
RelBuilder relBuilder = call.builder();
RelNode newScanInput = createInnerProject(relBuilder, scanInput, toPushFields);
// mapping origin field index to new field index, used to rewrite WindowTableFunction and
// top project
Map<Integer, Integer> mapping = getFieldMapping(scan.getRowType().getFieldCount(), scanInputFieldCount, toPushFields);
// 3. create new window table function scan
LogicalTableFunctionScan newScan = createNewTableFunctionScan(relBuilder, scan, windowingStrategy.getTimeAttributeType(), newScanInput, mapping);
// 4. create top project
RelNode topProject = createTopProject(relBuilder, project, newScan, mapping);
call.transformTo(topProject);
}
use of org.apache.calcite.rel.logical.LogicalTableFunctionScan in project calcite by apache.
the class SqlToRelConverter method convertCollectionTable.
protected void convertCollectionTable(Blackboard bb, SqlCall call) {
final SqlOperator operator = call.getOperator();
if (operator == SqlStdOperatorTable.TABLESAMPLE) {
final String sampleName = SqlLiteral.unchain(call.operand(0)).getValueAs(String.class);
datasetStack.push(sampleName);
SqlCall cursorCall = call.operand(1);
SqlNode query = cursorCall.operand(0);
RelNode converted = convertQuery(query, false, false).rel;
bb.setRoot(converted, false);
datasetStack.pop();
return;
}
replaceSubQueries(bb, call, RelOptUtil.Logic.TRUE_FALSE_UNKNOWN);
// Expand table macro if possible. It's more efficient than
// LogicalTableFunctionScan.
final SqlCallBinding callBinding = new SqlCallBinding(bb.scope.getValidator(), bb.scope, call);
if (operator instanceof SqlUserDefinedTableMacro) {
final SqlUserDefinedTableMacro udf = (SqlUserDefinedTableMacro) operator;
final TranslatableTable table = udf.getTable(typeFactory, callBinding.operands());
final RelDataType rowType = table.getRowType(typeFactory);
RelOptTable relOptTable = RelOptTableImpl.create(null, rowType, table, udf.getNameAsId().names);
RelNode converted = toRel(relOptTable);
bb.setRoot(converted, true);
return;
}
Type elementType;
if (operator instanceof SqlUserDefinedTableFunction) {
SqlUserDefinedTableFunction udtf = (SqlUserDefinedTableFunction) operator;
elementType = udtf.getElementType(typeFactory, callBinding.operands());
} else {
elementType = null;
}
RexNode rexCall = bb.convertExpression(call);
final List<RelNode> inputs = bb.retrieveCursors();
Set<RelColumnMapping> columnMappings = getColumnMappings(operator);
LogicalTableFunctionScan callRel = LogicalTableFunctionScan.create(cluster, inputs, rexCall, elementType, validator.getValidatedNodeType(call), columnMappings);
bb.setRoot(callRel, true);
afterTableFunction(bb, call, callRel);
}
Aggregations