package eu.stratosphere.sopremo.expressions; import eu.stratosphere.sopremo.EvaluationContext; import eu.stratosphere.sopremo.type.IJsonNode; import eu.stratosphere.sopremo.type.TypeCoercer; /** * Converts the result of an evaluation to a various number of node types. */ @OptimizerHints(scope = Scope.NUMBER) public class CoerceExpression extends EvaluationExpression { /** * */ private static final long serialVersionUID = 1954495592440005318L; private final Class<IJsonNode> targetType; private CachingExpression<IJsonNode> valueExpression; /** * Initializes a CoerceExpression with the given value and the given type. * * @param targetType * the class of the node the result should be converted to * @param value * the expression which evaluates to the result */ @SuppressWarnings("unchecked") public CoerceExpression(final Class<? extends IJsonNode> targetType, final EvaluationExpression value) { this.targetType = (Class<IJsonNode>) targetType; this.valueExpression = CachingExpression.ofSubclass(value, IJsonNode.class); } /** * Initializes a CoerceExpression with the given type. * * @param targetType * the class of the node the result should be converted to */ public CoerceExpression(final Class<? extends IJsonNode> targetType) { this(targetType, EvaluationExpression.VALUE); } /** * Returns the valueExpression. * * @return the valueExpression */ public EvaluationExpression getValueExpression() { return this.valueExpression; } /** * Sets a new valueExpression. * * @param valueExpression * the {@link EvaluationExpression} that should be set as the new valueExpression */ public void setValueExpression(final EvaluationExpression valueExpression) { if (valueExpression == null) throw new NullPointerException("valueExpression must not be null"); this.valueExpression = CachingExpression.ofSubclass(valueExpression, IJsonNode.class); } @Override public IJsonNode evaluate(final IJsonNode node, final IJsonNode target, final EvaluationContext context) { return TypeCoercer.INSTANCE.coerce(this.valueExpression.evaluate(node, context), target, this.targetType); } /* * (non-Javadoc) * @see * eu.stratosphere.sopremo.expressions.EvaluationExpression#transformRecursively(eu.stratosphere.sopremo.expressions * .TransformFunction) */ @SuppressWarnings("unchecked") @Override public EvaluationExpression transformRecursively(final TransformFunction function) { this.valueExpression = (CachingExpression<IJsonNode>) this.valueExpression.transformRecursively(function); return function.call(this); } @Override public void toString(final StringBuilder builder) { builder.append('(').append(this.targetType).append(')'); if (this.valueExpression != EvaluationExpression.VALUE) builder.append(' ').append(this.valueExpression); } @Override public int hashCode() { final int prime = 31; int result = super.hashCode(); result = prime * result + this.targetType.hashCode(); result = prime * result + this.valueExpression.hashCode(); return result; } @Override public boolean equals(final Object obj) { if (!super.equals(obj)) return false; final CoerceExpression other = (CoerceExpression) obj; return this.targetType == other.targetType && this.valueExpression.equals(other.valueExpression); } }