Java Code Examples for org.apache.calcite.rex.RexCall#getOperator()

The following examples show how to use org.apache.calcite.rex.RexCall#getOperator() . You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example 1
Source File: ProjectRelBase.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
@Override
public Boolean visitCall(RexCall call) {
  if (call.getOperator() == SqlStdOperatorTable.ITEM) {
    final RexNode op0 = call.getOperands().get(0);
    final RexNode op1 = call.getOperands().get(1);

    if (op0 instanceof RexInputRef &&
        op1 instanceof RexLiteral && ((RexLiteral) op1).getTypeName().getFamily() == SqlTypeFamily.CHARACTER) {
      return true;
    } else if (op0 instanceof RexCall &&
        op1 instanceof RexLiteral && ((RexLiteral) op1).getTypeName().getFamily() == SqlTypeFamily.CHARACTER) {
      return op0.accept(this);
    }
  }

  return false;
}
 
Example 2
Source File: GeodeRules.java    From calcite with Apache License 2.0 6 votes vote down vote up
@Override public String visitCall(RexCall call) {
  final List<String> strings = new ArrayList<>();
  visitList(call.operands, strings);
  if (call.getOperator() == SqlStdOperatorTable.ITEM) {
    final RexNode op1 = call.getOperands().get(1);
    if (op1 instanceof RexLiteral) {
      if (op1.getType().getSqlTypeName() == SqlTypeName.INTEGER) {
        return stripQuotes(strings.get(0)) + "[" + ((RexLiteral) op1).getValue2() + "]";
      } else if (op1.getType().getSqlTypeName() == SqlTypeName.CHAR) {
        return stripQuotes(strings.get(0)) + "." + ((RexLiteral) op1).getValue2();
      }
    }
  }

  return super.visitCall(call);
}
 
Example 3
Source File: ElasticsearchRules.java    From calcite with Apache License 2.0 6 votes vote down vote up
/**
 * Returns 'string' if it is a call to item['string'], null otherwise.
 * @param call current relational expression
 * @return literal value
 */
private static String isItemCall(RexCall call) {
  if (call.getOperator() != SqlStdOperatorTable.ITEM) {
    return null;
  }
  final RexNode op0 = call.getOperands().get(0);
  final RexNode op1 = call.getOperands().get(1);

  if (op0 instanceof RexInputRef
      && ((RexInputRef) op0).getIndex() == 0
      && op1 instanceof RexLiteral
      && ((RexLiteral) op1).getValue2() instanceof String) {
    return (String) ((RexLiteral) op1).getValue2();
  }
  return null;
}
 
Example 4
Source File: MongoRules.java    From calcite with Apache License 2.0 5 votes vote down vote up
/** Returns 'string' if it is a call to item['string'], null otherwise. */
static String isItem(RexCall call) {
  if (call.getOperator() != SqlStdOperatorTable.ITEM) {
    return null;
  }
  final RexNode op0 = call.operands.get(0);
  final RexNode op1 = call.operands.get(1);
  if (op0 instanceof RexInputRef
      && ((RexInputRef) op0).getIndex() == 0
      && op1 instanceof RexLiteral
      && ((RexLiteral) op1).getValue2() instanceof String) {
    return (String) ((RexLiteral) op1).getValue2();
  }
  return null;
}
 
Example 5
Source File: JdbcRules.java    From calcite with Apache License 2.0 5 votes vote down vote up
@Override public Void visitCall(RexCall call) {
  SqlOperator operator = call.getOperator();
  if (operator instanceof SqlFunction
      && ((SqlFunction) operator).getFunctionType().isUserDefined()) {
    containsUsedDefinedFunction |= true;
  }
  return super.visitCall(call);
}
 
Example 6
Source File: ElasticsearchFilter.java    From dk-fitting with Apache License 2.0 5 votes vote down vote up
private String isItem(RexCall call) {
    if (call.getOperator() != SqlStdOperatorTable.ITEM) {
        return null;
    }
    final RexNode op0 = call.getOperands().get(0);
    final RexNode op1 = call.getOperands().get(1);

    if (op0 instanceof RexInputRef
            && ((RexInputRef) op0).getIndex() == 0
            && op1 instanceof RexLiteral
            && ((RexLiteral) op1).getValue2() instanceof String) {
        return (String) ((RexLiteral) op1).getValue2();
    }
    return null;
}
 
Example 7
Source File: TupleExpressionVisitor.java    From kylin-on-parquet-v2 with Apache License 2.0 5 votes vote down vote up
@Override
public TupleExpression visitCall(RexCall call) {
    SqlOperator op = call.getOperator();
    if (op instanceof SqlCastFunction) {
        return call.getOperands().get(0).accept(this);
    } else if (op instanceof SqlUserDefinedFunction) {
        if (op.getName().equals("QUARTER")) {
            return visitFirstRexInputRef(call);
        }
    }

    TupleExpression tupleExpression;
    switch (op.getKind()) {
    case PLUS:
        tupleExpression = getBinaryTupleExpression(call, TupleExpression.ExpressionOperatorEnum.PLUS);
        break;
    case MINUS:
        tupleExpression = getBinaryTupleExpression(call, TupleExpression.ExpressionOperatorEnum.MINUS);
        break;
    case TIMES:
        tupleExpression = getBinaryTupleExpression(call, TupleExpression.ExpressionOperatorEnum.MULTIPLE);
        break;
    case DIVIDE:
        tupleExpression = getBinaryTupleExpression(call, TupleExpression.ExpressionOperatorEnum.DIVIDE);
        break;
    case CASE:
        tupleExpression = getCaseTupleExpression(call);
        break;
    default:
        tupleExpression = getRexCallTupleExpression(call);
    }
    if (ifVerify) {
        tupleExpression.verify();
    }
    return tupleExpression;
}
 
Example 8
Source File: FilterRemoveIsNotDistinctFromRule.java    From calcite with Apache License 2.0 5 votes vote down vote up
public RexNode visitCall(RexCall call) {
  RexNode newCall = super.visitCall(call);

  if (call.getOperator()
      == SqlStdOperatorTable.IS_NOT_DISTINCT_FROM) {
    RexCall tmpCall = (RexCall) newCall;
    newCall =
        RelOptUtil.isDistinctFrom(
            rexBuilder,
            tmpCall.operands.get(0),
            tmpCall.operands.get(1),
            true);
  }
  return newCall;
}
 
Example 9
Source File: RewriteAsBinaryOperators.java    From Bats with Apache License 2.0 5 votes vote down vote up
@Override
public RexNode visitCall(RexCall call) {
  SqlOperator op = call.getOperator();
  SqlKind kind = op.getKind();
  RelDataType type = call.getType();
  if (kind == SqlKind.OR || kind == SqlKind.AND) {
    if (call.getOperands().size() > 2) {
      List<RexNode> children = new ArrayList<>(call.getOperands());
      RexNode left = children.remove(0).accept(this);
      RexNode right = builder.makeCall(type, op, children).accept(this);
      return builder.makeCall(type, op, ImmutableList.of(left, right));
    }
  }
  return builder.makeCall(type, op, visitChildren(call));
}
 
Example 10
Source File: ReduceDecimalsRule.java    From Bats with Apache License 2.0 5 votes vote down vote up
/**
 * Rewrites a call, if required, or returns the original call
 */
private RexNode rewriteCall(RexCall call) {
    SqlOperator operator = call.getOperator();
    if (!operator.requiresDecimalExpansion()) {
        return call;
    }

    RexExpander expander = getExpander(call);
    if (expander.canExpand(call)) {
        return expander.expand(call);
    }
    return call;
}
 
Example 11
Source File: EnumerableTableFunctionScan.java    From calcite with Apache License 2.0 5 votes vote down vote up
private boolean isImplementorDefined(RexCall call) {
  if (call.getOperator() instanceof SqlWindowTableFunction
      && RexImpTable.INSTANCE.get((SqlWindowTableFunction) call.getOperator()) != null) {
    return true;
  }
  return false;
}
 
Example 12
Source File: RexImpTable.java    From calcite with Apache License 2.0 5 votes vote down vote up
private ParameterExpression genValueStatement(
    final RexToLixTranslator translator,
    final RexCall call, final List<Expression> argValueList,
    final Expression condition) {
  List<Expression> optimizedArgValueList = argValueList;
  if (harmonize) {
    optimizedArgValueList =
        harmonize(optimizedArgValueList, translator, call);
  }
  optimizedArgValueList = unboxIfNecessary(optimizedArgValueList);

  final Expression callValue =
      implementSafe(translator, call, optimizedArgValueList);

  // In general, RexCall's type is correct for code generation
  // and thus we should ensure the consistency.
  // However, for some special cases (e.g., TableFunction),
  // the implementation's type is correct, we can't convert it.
  final SqlOperator op = call.getOperator();
  final Type returnType = translator.typeFactory.getJavaClass(call.getType());
  final boolean noConvert = (returnType == null)
          || (returnType == callValue.getType())
          || (op instanceof SqlUserDefinedTableMacro)
          || (op instanceof SqlUserDefinedTableFunction);
  final Expression convertedCallValue =
          noConvert
          ? callValue
          : EnumUtils.convert(callValue, returnType);

  final Expression valueExpression =
      Expressions.condition(condition,
          getIfTrue(convertedCallValue.getType(), argValueList),
          convertedCallValue);
  final ParameterExpression value =
      Expressions.parameter(convertedCallValue.getType(),
          translator.getBlockBuilder().newName(getVariableName() + "_value"));
  translator.getBlockBuilder().add(
      Expressions.declare(Modifier.FINAL, value, valueExpression));
  return value;
}
 
Example 13
Source File: RelMdColumnUniqueness.java    From calcite with Apache License 2.0 4 votes vote down vote up
private Boolean areProjectColumnsUnique(
    SingleRel rel, RelMetadataQuery mq,
    ImmutableBitSet columns, boolean ignoreNulls, List<RexNode> projExprs) {
  RelDataTypeFactory typeFactory = rel.getCluster().getTypeFactory();
  ImmutableBitSet.Builder childColumns = ImmutableBitSet.builder();
  for (int bit : columns) {
    RexNode projExpr = projExprs.get(bit);
    if (projExpr instanceof RexInputRef) {
      childColumns.set(((RexInputRef) projExpr).getIndex());
    } else if (projExpr instanceof RexCall && ignoreNulls) {
      // If the expression is a cast such that the types are the same
      // except for the nullability, then if we're ignoring nulls,
      // it doesn't matter whether the underlying column reference
      // is nullable.  Check that the types are the same by making a
      // nullable copy of both types and then comparing them.
      RexCall call = (RexCall) projExpr;
      if (call.getOperator() != SqlStdOperatorTable.CAST) {
        continue;
      }
      RexNode castOperand = call.getOperands().get(0);
      if (!(castOperand instanceof RexInputRef)) {
        continue;
      }
      RelDataType castType =
          typeFactory.createTypeWithNullability(
              projExpr.getType(), true);
      RelDataType origType = typeFactory.createTypeWithNullability(
          castOperand.getType(),
          true);
      if (castType.equals(origType)) {
        childColumns.set(((RexInputRef) castOperand).getIndex());
      }
    } else {
      // If the expression will not influence uniqueness of the
      // projection, then skip it.
      continue;
    }
  }

  // If no columns can affect uniqueness, then return unknown
  if (childColumns.cardinality() == 0) {
    return null;
  }

  return mq.areColumnsUnique(rel.getInput(), childColumns.build(),
      ignoreNulls);
}
 
Example 14
Source File: CallTransformer.java    From dremio-oss with Apache License 2.0 4 votes vote down vote up
/**
 * Adjust the SqlOperator for this operator based on its arguments.
 */
public SqlOperator getAlternateOperator(RexCall call) {
  return call.getOperator();
}
 
Example 15
Source File: RelDecorrelator.java    From Bats with Apache License 2.0 4 votes vote down vote up
@Override
public RexNode visitCall(final RexCall call) {
    RexNode newCall;

    boolean[] update = { false };
    List<RexNode> clonedOperands = visitList(call.getOperands(), update);
    if (update[0]) {
        SqlOperator operator = call.getOperator();

        boolean isSpecialCast = false;
        if (operator instanceof SqlFunction) {
            SqlFunction function = (SqlFunction) operator;
            if (function.getKind() == SqlKind.CAST) {
                if (call.getOperands().size() < 2) {
                    isSpecialCast = true;
                }
            }
        }

        final RelDataType newType;
        if (!isSpecialCast) {
            // TODO: ideally this only needs to be called if the result
            // type will also change. However, since that requires
            // support from type inference rules to tell whether a rule
            // decides return type based on input types, for now all
            // operators will be recreated with new type if any operand
            // changed, unless the operator has "built-in" type.
            newType = rexBuilder.deriveReturnType(operator, clonedOperands);
        } else {
            // Use the current return type when creating a new call, for
            // operators with return type built into the operator
            // definition, and with no type inference rules, such as
            // cast function with less than 2 operands.

            // TODO: Comments in RexShuttle.visitCall() mention other
            // types in this category. Need to resolve those together
            // and preferably in the base class RexShuttle.
            newType = call.getType();
        }
        newCall = rexBuilder.makeCall(newType, operator, clonedOperands);
    } else {
        newCall = call;
    }

    if (projectPulledAboveLeftCorrelator && (nullIndicator != null)) {
        return createCaseExpression(nullIndicator, rexBuilder.constantNull(), newCall);
    }
    return newCall;
}
 
Example 16
Source File: RelDecorrelator.java    From flink with Apache License 2.0 4 votes vote down vote up
@Override public RexNode visitCall(final RexCall call) {
  RexNode newCall;

  boolean[] update = {false};
  List<RexNode> clonedOperands = visitList(call.operands, update);
  if (update[0]) {
    SqlOperator operator = call.getOperator();

    boolean isSpecialCast = false;
    if (operator instanceof SqlFunction) {
      SqlFunction function = (SqlFunction) operator;
      if (function.getKind() == SqlKind.CAST) {
        if (call.operands.size() < 2) {
          isSpecialCast = true;
        }
      }
    }

    final RelDataType newType;
    if (!isSpecialCast) {
      // TODO: ideally this only needs to be called if the result
      // type will also change. However, since that requires
      // support from type inference rules to tell whether a rule
      // decides return type based on input types, for now all
      // operators will be recreated with new type if any operand
      // changed, unless the operator has "built-in" type.
      newType = rexBuilder.deriveReturnType(operator, clonedOperands);
    } else {
      // Use the current return type when creating a new call, for
      // operators with return type built into the operator
      // definition, and with no type inference rules, such as
      // cast function with less than 2 operands.

      // TODO: Comments in RexShuttle.visitCall() mention other
      // types in this category. Need to resolve those together
      // and preferably in the base class RexShuttle.
      newType = call.getType();
    }
    newCall =
        rexBuilder.makeCall(
            newType,
            operator,
            clonedOperands);
  } else {
    newCall = call;
  }

  if (projectPulledAboveLeftCorrelator && (nullIndicator != null)) {
    return createCaseExpression(
        nullIndicator,
        rexBuilder.constantNull(),
        newCall);
  }
  return newCall;
}
 
Example 17
Source File: HiveUDFImplementor.java    From marble with Apache License 2.0 4 votes vote down vote up
@Override public Expression implement(RexToLixTranslator translator,
    RexCall call, List<Expression> translatedOperands) {
  try {
    SqlOperator operator = call.getOperator();
    int hiveUdfId = HiveUDFInstanceCollecterPerSqlQuery.get().getSizeOfStashedHiveUDFInstance();
    String udfInstanceName = "udfInstance_" + hiveUdfId;

    HiveUDFInstanceCollecterPerSqlQuery.get().incrementSizeOfStashedHiveUDFInstance();

    ParameterExpression udfInstanceVariableExpr = Expressions
        .parameter(Types.of(GenericUDF.class, Object.class),
            "hiveUDFInstanceHolder." + udfInstanceName);

    ParameterExpression udfInstanceVariableLocalExpr = Expressions
        .parameter(Types.of(GenericUDF.class, Object.class),
            udfInstanceName);

    HiveUDFInstanceCollecterPerSqlQuery.get()
        .getStashedFieldsForHiveUDFInstanceHolder()
        .add(generateUdfInstanceDeclaration(operator.getName(), operator.getSyntax(), udfInstanceName));

    Expression argTypeArrayExpr = generateArgsTypeExpr(call, translatedOperands);

    Expression argsExpr = new NewArrayExpression(Object.class, 1, null,
        translatedOperands);

    String outputOiName = "udfOutputOi_" + hiveUdfId;

    ParameterExpression udfOutputOiVariableExpr = Expressions
        .parameter(Types.of(GenericUDF.class, Object.class),
            "hiveUDFInstanceHolder." + outputOiName);

    HiveUDFInstanceCollecterPerSqlQuery.get()
        .getStashedFieldsForHiveUDFInstanceHolder()
        .add(generateUdfOutputOIDeclaration(udfInstanceVariableLocalExpr, argTypeArrayExpr, outputOiName));

    Expression callExpr = Expressions.call(CALL_GENERIC_UDF_METHOD,
        Arrays.asList(udfInstanceVariableExpr, argsExpr, argTypeArrayExpr, udfOutputOiVariableExpr));
    String castMethodName =
        TypeConvertUtil.CALCITE_SQL_TYPE_2_CAST_METHOD.get(
            call.type.getSqlTypeName());
    Method castMethod = TypeConvertUtil.class.getMethod(castMethodName,
        Object.class);
    Expression castExpr = Expressions.call(castMethod, callExpr);
    return castExpr;

  } catch (Exception e) {
    throw new RuntimeException(e);
  }
}
 
Example 18
Source File: ReduceExpressionsRule.java    From Bats with Apache License 2.0 4 votes vote down vote up
private void analyzeCall(RexCall call, Constancy callConstancy) {
  parentCallTypeStack.push(call.getOperator());

  // visit operands, pushing their states onto stack
  super.visitCall(call);

  // look for NON_CONSTANT operands
  int operandCount = call.getOperands().size();
  List<Constancy> operandStack = Util.last(stack, operandCount);
  for (Constancy operandConstancy : operandStack) {
    if (operandConstancy == Constancy.NON_CONSTANT) {
      callConstancy = Constancy.NON_CONSTANT;
    }
  }

  // Even if all operands are constant, the call itself may
  // be non-deterministic.
  if (!call.getOperator().isDeterministic()) {
    callConstancy = Constancy.NON_CONSTANT;
  } else if (call.getOperator().isDynamicFunction()) {
    // We can reduce the call to a constant, but we can't
    // cache the plan if the function is dynamic.
    // For now, treat it same as non-deterministic.
    callConstancy = Constancy.NON_CONSTANT;
  }

  // Row operator itself can't be reduced to a literal, but if
  // the operands are constants, we still want to reduce those
  if ((callConstancy == Constancy.REDUCIBLE_CONSTANT)
      && (call.getOperator() instanceof SqlRowOperator)) {
    callConstancy = Constancy.NON_CONSTANT;
  }

  if (callConstancy == Constancy.NON_CONSTANT) {
    // any REDUCIBLE_CONSTANT children are now known to be maximal
    // reducible subtrees, so they can be added to the result
    // list
    for (int iOperand = 0; iOperand < operandCount; ++iOperand) {
      Constancy constancy = operandStack.get(iOperand);
      if (constancy == Constancy.REDUCIBLE_CONSTANT) {
        addResult(call.getOperands().get(iOperand));
      }
    }

    // if this cast expression can't be reduced to a literal,
    // then see if we can remove the cast
    if (call.getOperator() == SqlStdOperatorTable.CAST) {
      reduceCasts(call);
    }
  }

  // pop operands off of the stack
  operandStack.clear();

  // pop this parent call operator off the stack
  parentCallTypeStack.pop();

  // push constancy result for this call onto stack
  stack.add(callConstancy);
}
 
Example 19
Source File: RelJson.java    From Bats with Apache License 2.0 4 votes vote down vote up
private Object toJson(RexNode node) {
  final Map<String, Object> map;
  switch (node.getKind()) {
  case FIELD_ACCESS:
    map = jsonBuilder.map();
    final RexFieldAccess fieldAccess = (RexFieldAccess) node;
    map.put("field", fieldAccess.getField().getName());
    map.put("expr", toJson(fieldAccess.getReferenceExpr()));
    return map;
  case LITERAL:
    final RexLiteral literal = (RexLiteral) node;
    final Object value = literal.getValue3();
    map = jsonBuilder.map();
    map.put("literal", value);
    map.put("type", toJson(node.getType()));
    return map;
  case INPUT_REF:
  case LOCAL_REF:
    map = jsonBuilder.map();
    map.put("input", ((RexSlot) node).getIndex());
    map.put("name", ((RexSlot) node).getName());
    return map;
  case CORREL_VARIABLE:
    map = jsonBuilder.map();
    map.put("correl", ((RexCorrelVariable) node).getName());
    map.put("type", toJson(node.getType()));
    return map;
  default:
    if (node instanceof RexCall) {
      final RexCall call = (RexCall) node;
      map = jsonBuilder.map();
      map.put("op", toJson(call.getOperator()));
      final List<Object> list = jsonBuilder.list();
      for (RexNode operand : call.getOperands()) {
        list.add(toJson(operand));
      }
      map.put("operands", list);
      switch (node.getKind()) {
      case CAST:
        map.put("type", toJson(node.getType()));
      }
      if (call.getOperator() instanceof SqlFunction) {
        if (((SqlFunction) call.getOperator()).getFunctionType().isUserDefined()) {
          SqlOperator op = call.getOperator();
          map.put("class", op.getClass().getName());
          map.put("type", toJson(node.getType()));
          map.put("deterministic", op.isDeterministic());
          map.put("dynamic", op.isDynamicFunction());
        }
      }
      if (call instanceof RexOver) {
        RexOver over = (RexOver) call;
        map.put("distinct", over.isDistinct());
        map.put("type", toJson(node.getType()));
        map.put("window", toJson(over.getWindow()));
      }
      return map;
    }
    throw new UnsupportedOperationException("unknown rex " + node);
  }
}
 
Example 20
Source File: RewriteProjectToFlattenRule.java    From dremio-oss with Apache License 2.0 3 votes vote down vote up
@Override
public RexNode visitCall(RexCall function, LevelHolder outgoingLevel) {
  if (!(function.getOperator() instanceof SqlFlattenOperator)) {
    return super.visitCall(function, outgoingLevel);
  }


  final int index = ((SqlFlattenOperator) function.getOperator()).getIndex();

  FlattenExpression flattenOutput = flattenOutputs.get(index);

  if(flattenOutput != null){
    outgoingLevel.index = flattenOutput.level + 1;
    return flattenOutput.inputReference;

  } else {
    Preconditions.checkArgument(function.getOperands().size() == 1, "Flatten only supports a single operand.");

    LevelHolder inputLevel = new LevelHolder();
    RexNode newRexInput = function.getOperands().get(0).accept(this, inputLevel);


    final MutableRexInputRef inputPointer = new MutableRexInputRef(newRexInput.getType());
    projectLevels.put(inputLevel.index, new ProjectSlotHolder(newRexInput, inputPointer));


    final FlattenExpression flatten = new FlattenExpression(inputLevel.index, inputPointer);
    flattenOutputs.put(index, flatten);
    flattenLevels.put(inputLevel.index, flatten);

    // the output level will be one more than the input.
    outgoingLevel.index = inputLevel.index + 1;
    return inputPointer;
  }

}