private static Object evaluate(Expression expression) { Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypes(TEST_SESSION, METADATA, SQL_PARSER, SYMBOL_TYPES, expression, emptyList(), WarningCollector.NOOP); ExpressionInterpreter interpreter = expressionInterpreter(expression, METADATA, TEST_SESSION, expressionTypes); return interpreter.evaluate(); }
private Expression simplifyExpression(Session session, Expression predicate, TypeProvider types) { // TODO reuse com.facebook.presto.sql.planner.iterative.rule.SimplifyExpressions.rewrite Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypes(session, predicate, types); ExpressionInterpreter interpreter = ExpressionInterpreter.expressionOptimizer(predicate, metadata, session, expressionTypes); Object value = interpreter.optimize(NoOpSymbolResolver.INSTANCE); if (value == null) { // Expression evaluates to SQL null, which in Filter is equivalent to false. This assumes the expression is a top-level expression (eg. not in NOT). value = false; } return literalEncoder.toExpression(value, BOOLEAN); }
public static ExpressionInterpreter expressionInterpreter(Expression expression, Metadata metadata, Session session, Map<NodeRef<Expression>, Type> expressionTypes) { return new ExpressionInterpreter(expression, metadata, session, expressionTypes, false); }
public InterpretedPageProjection( Expression expression, TypeProvider symbolTypes, Map<Symbol, Integer> symbolToInputMappings, Metadata metadata, SqlParser sqlParser, Session session) { SymbolToInputParameterRewriter rewriter = new SymbolToInputParameterRewriter(symbolTypes, symbolToInputMappings); Expression rewritten = rewriter.rewrite(expression); this.inputChannels = new InputChannels(rewriter.getInputChannels()); this.deterministic = DeterminismEvaluator.isDeterministic(expression); // analyze rewritten expression so we can know the type of every expression in the tree List<Type> inputTypes = rewriter.getInputTypes(); ImmutableMap.Builder<Integer, Type> parameterTypes = ImmutableMap.builder(); for (int parameter = 0; parameter < inputTypes.size(); parameter++) { Type type = inputTypes.get(parameter); parameterTypes.put(parameter, type); } Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypesFromInput(session, metadata, sqlParser, parameterTypes.build(), rewritten, emptyList(), WarningCollector.NOOP); this.evaluator = ExpressionInterpreter.expressionInterpreter(rewritten, metadata, session, expressionTypes); blockBuilder = evaluator.getType().createBlockBuilder(null, 1); }
private boolean filter(Page page, int position) { return TRUE.equals(evaluator.evaluate(position, page)); } }
public InterpretedPageFilter( Expression expression, TypeProvider symbolTypes, Map<Symbol, Integer> symbolToInputMappings, Metadata metadata, SqlParser sqlParser, Session session) { SymbolToInputParameterRewriter rewriter = new SymbolToInputParameterRewriter(symbolTypes, symbolToInputMappings); Expression rewritten = rewriter.rewrite(expression); this.inputChannels = new InputChannels(rewriter.getInputChannels()); this.deterministic = DeterminismEvaluator.isDeterministic(expression); // analyze rewritten expression so we can know the type of every expression in the tree List<Type> inputTypes = rewriter.getInputTypes(); ImmutableMap.Builder<Integer, Type> parameterTypes = ImmutableMap.builder(); for (int parameter = 0; parameter < inputTypes.size(); parameter++) { Type type = inputTypes.get(parameter); parameterTypes.put(parameter, type); } Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypesFromInput(session, metadata, sqlParser, parameterTypes.build(), rewritten, emptyList(), WarningCollector.NOOP); this.evaluator = ExpressionInterpreter.expressionInterpreter(rewritten, metadata, session, expressionTypes); }
private List<Object> getSymbolValues(ValuesNode valuesNode, int symbolId, Session session, Type symbolType) { if (UNKNOWN.equals(symbolType)) { // special casing for UNKNOWN as evaluateConstantExpression does not handle that return IntStream.range(0, valuesNode.getRows().size()) .mapToObj(rowId -> null) .collect(toList()); } return valuesNode.getRows().stream() .map(row -> row.get(symbolId)) .map(expression -> evaluateConstantExpression(expression, symbolType, metadata, session, ImmutableList.of())) .collect(toList()); }
@Override public boolean process() { checkState(result == null, "result has been generated"); int length = selectedPositions.getOffset() + selectedPositions.size(); if (selectedPositions.isList()) { int[] positions = selectedPositions.getPositions(); while (nextIndexOrPosition < length) { writeNativeValue(evaluator.getType(), blockBuilder, evaluator.evaluate(positions[nextIndexOrPosition], page)); nextIndexOrPosition++; if (yieldSignal.isSet()) { return false; } } } else { while (nextIndexOrPosition < length) { writeNativeValue(evaluator.getType(), blockBuilder, evaluator.evaluate(nextIndexOrPosition, page)); nextIndexOrPosition++; if (yieldSignal.isSet()) { return false; } } } result = blockBuilder.build(); blockBuilder = blockBuilder.newBlockBuilderLike(null); return true; }
private boolean isCandidate(Map<ColumnHandle, NullableValue> bindings) { if (intersection(bindings.keySet(), arguments).isEmpty()) { return true; } LookupSymbolResolver inputs = new LookupSymbolResolver(assignments, bindings); // Skip pruning if evaluation fails in a recoverable way. Failing here can cause // spurious query failures for partitions that would otherwise be filtered out. Object optimized = TryFunction.evaluate(() -> evaluator.optimize(inputs), true); // If any conjuncts evaluate to FALSE or null, then the whole predicate will never be true and so the partition should be pruned if (Boolean.FALSE.equals(optimized) || optimized == null || optimized instanceof NullLiteral) { return false; } return true; } }
public LayoutConstraintEvaluator(Metadata metadata, SqlParser parser, Session session, TypeProvider types, Map<Symbol, ColumnHandle> assignments, Expression expression) { this.assignments = assignments; Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypes(session, metadata, parser, types, expression, emptyList(), WarningCollector.NOOP); evaluator = ExpressionInterpreter.expressionOptimizer(expression, metadata, session, expressionTypes); arguments = SymbolsExtractor.extractUnique(expression).stream() .map(assignments::get) .collect(toImmutableSet()); }
private Object processWithExceptionHandling(Expression expression, Object context) { if (expression == null) { return null; } try { return process(expression, context); } catch (RuntimeException e) { // HACK // Certain operations like 0 / 0 or likeExpression may throw exceptions. // Wrap them a FunctionCall that will throw the exception if the expression is actually executed return createFailureFunction(e, type(expression)); } }
@Override public boolean filter(RecordCursor cursor) { return evaluator.evaluate(cursor) == TRUE; }
public InterpretedProjectionFunction( Expression expression, Map<Symbol, Type> symbolTypes, Map<Symbol, Integer> symbolToInputMappings, Metadata metadata, SqlParser sqlParser, Session session) { // pre-compute symbol -> input mappings and replace the corresponding nodes in the tree Expression rewritten = ExpressionTreeRewriter.rewriteWith(new SymbolToInputRewriter(symbolToInputMappings), expression); // analyze expression so we can know the type of every expression in the tree ImmutableMap.Builder<Integer, Type> inputTypes = ImmutableMap.builder(); for (Map.Entry<Symbol, Integer> entry : symbolToInputMappings.entrySet()) { inputTypes.put(entry.getValue(), symbolTypes.get(entry.getKey())); } IdentityHashMap<Expression, Type> expressionTypes = getExpressionTypesFromInput(session, metadata, sqlParser, inputTypes.build(), rewritten); this.type = requireNonNull(expressionTypes.get(rewritten), "type is null"); evaluator = ExpressionInterpreter.expressionInterpreter(rewritten, metadata, session, expressionTypes); InputReferenceExtractor inputReferenceExtractor = new InputReferenceExtractor(); inputReferenceExtractor.process(rewritten, null); this.inputChannels = inputReferenceExtractor.getInputChannels(); this.deterministic = DeterminismEvaluator.isDeterministic(expression); }
public static Object evaluateConstantExpression(Expression expression, Type expectedType, Metadata metadata, Session session, List<Expression> parameters) { ExpressionAnalyzer analyzer = createConstantAnalyzer(metadata, session, parameters, WarningCollector.NOOP); analyzer.analyze(expression, Scope.create()); Type actualType = analyzer.getExpressionTypes().get(NodeRef.of(expression)); if (!metadata.getTypeManager().canCoerce(actualType, expectedType)) { throw new SemanticException(SemanticErrorCode.TYPE_MISMATCH, expression, format("Cannot cast type %s to %s", actualType.getTypeSignature(), expectedType.getTypeSignature())); } Map<NodeRef<Expression>, Type> coercions = ImmutableMap.<NodeRef<Expression>, Type>builder() .putAll(analyzer.getExpressionCoercions()) .put(NodeRef.of(expression), expectedType) .build(); return evaluateConstantExpression(expression, coercions, analyzer.getTypeOnlyCoercions(), metadata, session, ImmutableSet.of(), parameters); }
/** * Evaluates an expression's response to binding the specified input symbols to NULL */ private Object nullInputEvaluator(final Collection<Symbol> nullSymbols, Expression expression) { Map<NodeRef<Expression>, Type> expressionTypes = getExpressionTypes( session, metadata, sqlParser, symbolAllocator.getTypes(), expression, emptyList(), /* parameters have already been replaced */ WarningCollector.NOOP); return ExpressionInterpreter.expressionOptimizer(expression, metadata, session, expressionTypes) .optimize(symbol -> nullSymbols.contains(symbol) ? null : symbol.toSymbolReference()); }
for (int i = 0; i < row.size(); i++) { Object result = ExpressionInterpreter.expressionInterpreter(row.get(i), metadata, context.getSession(), expressionTypes).evaluate(); writeNativeValue(outputTypes.get(i), pageBuilder.getBlockBuilder(i), result);
@Override public boolean filter(int position, Block... blocks) { return evaluator.evaluate(position, blocks) == TRUE; }
public InterpretedFilterFunction( Expression predicate, Map<Symbol, Type> symbolTypes, Map<Symbol, Integer> symbolToInputMappings, Metadata metadata, SqlParser sqlParser, Session session) { // pre-compute symbol -> input mappings and replace the corresponding nodes in the tree Expression rewritten = ExpressionTreeRewriter.rewriteWith(new SymbolToInputRewriter(symbolToInputMappings), predicate); // analyze expression so we can know the type of every expression in the tree ImmutableMap.Builder<Integer, Type> inputTypes = ImmutableMap.builder(); for (Map.Entry<Symbol, Integer> entry : symbolToInputMappings.entrySet()) { inputTypes.put(entry.getValue(), symbolTypes.get(entry.getKey())); } IdentityHashMap<Expression, Type> expressionTypes = getExpressionTypesFromInput(session, metadata, sqlParser, inputTypes.build(), rewritten); evaluator = ExpressionInterpreter.expressionInterpreter(rewritten, metadata, session, expressionTypes); InputReferenceExtractor inputReferenceExtractor = new InputReferenceExtractor(); inputReferenceExtractor.process(rewritten, null); this.inputChannels = ImmutableSet.copyOf(inputReferenceExtractor.getInputChannels()); }
private Object evaluatePropertyValue(Expression expression, Type expectedType, Session session, Metadata metadata, List<Expression> parameters) { Expression rewritten = ExpressionTreeRewriter.rewriteWith(new ParameterRewriter(parameters), expression); Object value = evaluateConstantExpression(rewritten, expectedType, metadata, session, parameters); // convert to object value type of SQL type BlockBuilder blockBuilder = expectedType.createBlockBuilder(null, 1); writeNativeValue(expectedType, blockBuilder, value); Object objectValue = expectedType.getObjectValue(session.toConnectorSession(), blockBuilder, 0); if (objectValue == null) { throw new PrestoException(propertyError, format("Invalid null value for %s property", propertyType)); } return objectValue; } }
public static ExpressionInterpreter expressionOptimizer(Expression expression, Metadata metadata, Session session, Map<NodeRef<Expression>, Type> expressionTypes) { requireNonNull(expression, "expression is null"); requireNonNull(metadata, "metadata is null"); requireNonNull(session, "session is null"); return new ExpressionInterpreter(expression, metadata, session, expressionTypes, true); }