Ali Alsuliman has uploaded a new change for review. https://asterix-gerrit.ics.uci.edu/3145
Change subject: [ASTERIXDB-2516][RT] add support for deep comparison 1 ...................................................................... [ASTERIXDB-2516][RT] add support for deep comparison 1 - user model changes: no - storage format changes: no - interface changes: no Details: add support for deep comparison Change-Id: I623662861e6f3b1fdcff78f8edc0e3216ca10fe1 --- M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_circle/issue363_inequality_circle.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_duration/issue363_inequality_duration.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_interval/issue363_inequality_interval.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_line/issue363_inequality_line.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_point/issue363_inequality_point.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_polygon/issue363_inequality_polygon.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_rectangle/issue363_inequality_rectangle.1.adm M asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml A asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/ILogicalBinaryComparator.java A asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/LogicalComparatorUtil.java A asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalComplexBinaryComparator.java A asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalGenericBinaryComparator.java A asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalScalarBinaryComparator.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractComparisonEvaluator.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractIfEqualsEvaluator.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractValueComparisonEvaluator.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/EqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanOrEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanOrEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/MissingIfEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NanIfEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NegInfIfEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NotEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NullIfEqualsDescriptor.java M asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/PosInfIfEqualsDescriptor.java 27 files changed, 995 insertions(+), 172 deletions(-) git pull ssh://asterix-gerrit.ics.uci.edu:29418/asterixdb refs/changes/45/3145/1 diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_circle/issue363_inequality_circle.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_circle/issue363_inequality_circle.1.adm index e3b97f5..e3846b9 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_circle/issue363_inequality_circle.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_circle/issue363_inequality_circle.1.adm @@ -1 +1 @@ -[ ] +{ "circle0": null, "circle1": null, "circle2": null, "circle3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_duration/issue363_inequality_duration.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_duration/issue363_inequality_duration.1.adm index e3b97f5..60e80d9 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_duration/issue363_inequality_duration.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_duration/issue363_inequality_duration.1.adm @@ -1 +1 @@ -[ ] +{ "duration0": null, "duration1": null, "duration2": null, "duration3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_interval/issue363_inequality_interval.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_interval/issue363_inequality_interval.1.adm index e3b97f5..76c2bb0 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_interval/issue363_inequality_interval.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_interval/issue363_inequality_interval.1.adm @@ -1 +1 @@ -[ ] +{ "interval0": null, "interval1": null, "interval2": null, "interval3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_line/issue363_inequality_line.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_line/issue363_inequality_line.1.adm index e3b97f5..31cf931 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_line/issue363_inequality_line.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_line/issue363_inequality_line.1.adm @@ -1 +1 @@ -[ ] +{ "line0": null, "line1": null, "line2": null, "line3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_point/issue363_inequality_point.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_point/issue363_inequality_point.1.adm index e3b97f5..3e24175 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_point/issue363_inequality_point.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_point/issue363_inequality_point.1.adm @@ -1 +1 @@ -[ ] +{ "point0": null, "point1": null, "point2": null, "point3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_polygon/issue363_inequality_polygon.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_polygon/issue363_inequality_polygon.1.adm index e3b97f5..8a0655b 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_polygon/issue363_inequality_polygon.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_polygon/issue363_inequality_polygon.1.adm @@ -1 +1 @@ -[ ] +{ "polygon0": null, "polygon1": null, "polygon2": null, "polygon3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_rectangle/issue363_inequality_rectangle.1.adm b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_rectangle/issue363_inequality_rectangle.1.adm index e3b97f5..5429dcc 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_rectangle/issue363_inequality_rectangle.1.adm +++ b/asterixdb/asterix-app/src/test/resources/runtimets/results/comparison/issue363_inequality_rectangle/issue363_inequality_rectangle.1.adm @@ -1 +1 @@ -[ ] +{ "rectangle0": null, "rectangle1": null, "rectangle2": null, "rectangle3": null } \ No newline at end of file diff --git a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml index ceee5f9..d7ca047 100644 --- a/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml +++ b/asterixdb/asterix-app/src/test/resources/runtimets/testsuite_sqlpp.xml @@ -2303,43 +2303,36 @@ <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_duration"> <output-dir compare="Text">issue363_inequality_duration</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type duration</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_interval"> <output-dir compare="Text">issue363_inequality_interval</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type interval</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_point"> <output-dir compare="Text">issue363_inequality_point</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type point</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_line"> <output-dir compare="Text">issue363_inequality_line</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type line</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_polygon"> <output-dir compare="Text">issue363_inequality_polygon</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type polygon</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_rectangle"> <output-dir compare="Text">issue363_inequality_rectangle</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type rectangle</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> <compilation-unit name="issue363_inequality_circle"> <output-dir compare="Text">issue363_inequality_circle</output-dir> - <expected-error>Unsupported type: comparison operations (>, >=, <, and <=) cannot process input type circle</expected-error> </compilation-unit> </test-case> <test-case FilePath="comparison"> diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/ILogicalBinaryComparator.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/ILogicalBinaryComparator.java new file mode 100644 index 0000000..7f9769a --- /dev/null +++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/ILogicalBinaryComparator.java @@ -0,0 +1,57 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.asterix.dataflow.data.common; + +import org.apache.asterix.om.base.IAObject; +import org.apache.hyracks.api.exceptions.HyracksDataException; + +public interface ILogicalBinaryComparator { + enum Result { + MISSING, + NULL, + EQ, + LT, + GT, + MISMATCH + } + + enum Operation { + EQUALITY, + INEQUALITY + } + + static Result returnResult(int result) { + if (result == 0) { + return Result.EQ; + } else if (result < 0) { + return Result.LT; + } else { + return Result.GT; + } + } + + Result compare(byte[] leftBytes, int leftStart, int leftLen, byte[] rightBytes, int rightStart, int rightLen, + Operation operation) throws HyracksDataException; + + Result compare(byte[] leftBytes, int leftStart, int leftLen, IAObject rightConstant, Operation operation); + + Result compare(IAObject leftConstant, byte[] rightBytes, int rightStart, int rightLen, Operation operation); + + Result compare(IAObject leftConstant, IAObject rightConstant, Operation operation); +} diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/LogicalComparatorUtil.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/LogicalComparatorUtil.java new file mode 100644 index 0000000..5f20d3c --- /dev/null +++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/common/LogicalComparatorUtil.java @@ -0,0 +1,171 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.asterix.dataflow.data.common; + +import static org.apache.asterix.om.types.ATypeTag.BIGINT; +import static org.apache.asterix.om.types.ATypeTag.DOUBLE; +import static org.apache.asterix.om.types.ATypeTag.FLOAT; +import static org.apache.asterix.om.types.ATypeTag.INTEGER; +import static org.apache.asterix.om.types.ATypeTag.MISSING; +import static org.apache.asterix.om.types.ATypeTag.NULL; +import static org.apache.asterix.om.types.ATypeTag.SMALLINT; +import static org.apache.asterix.om.types.ATypeTag.TINYINT; + +import org.apache.asterix.dataflow.data.nontagged.comparators.LogicalComplexBinaryComparator; +import org.apache.asterix.dataflow.data.nontagged.comparators.LogicalGenericBinaryComparator; +import org.apache.asterix.dataflow.data.nontagged.comparators.LogicalScalarBinaryComparator; +import org.apache.asterix.dataflow.data.nontagged.serde.ADoubleSerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AFloatSerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt16SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt32SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt64SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt8SerializerDeserializer; +import org.apache.asterix.om.base.ADouble; +import org.apache.asterix.om.base.AFloat; +import org.apache.asterix.om.base.AInt16; +import org.apache.asterix.om.base.AInt32; +import org.apache.asterix.om.base.AInt64; +import org.apache.asterix.om.base.AInt8; +import org.apache.asterix.om.base.IAObject; +import org.apache.asterix.om.typecomputer.impl.TypeComputeUtils; +import org.apache.asterix.om.types.ATypeTag; +import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.types.IAType; +import org.apache.asterix.om.types.hierachy.ATypeHierarchy; + +public class LogicalComparatorUtil { + + public static ILogicalBinaryComparator createLogicalComparator(IAType left, IAType right) { + IAType leftType = TypeComputeUtils.getActualType(left); + IAType rightType = TypeComputeUtils.getActualType(right); + + if (leftType.getTypeTag().isDerivedType() && rightType.getTypeTag().isDerivedType()) { + return new LogicalComplexBinaryComparator(leftType, rightType); + } else if (leftType.getTypeTag() == ATypeTag.ANY || rightType.getTypeTag() == ATypeTag.ANY) { + return new LogicalGenericBinaryComparator(leftType, rightType); + } else { + return new LogicalScalarBinaryComparator(); + } + } + + public static ILogicalBinaryComparator.Result returnMissingOrNull(ATypeTag leftTag, ATypeTag rightTag) { + if (leftTag == MISSING || rightTag == MISSING) { + return ILogicalBinaryComparator.Result.MISSING; + } + if (leftTag == NULL || rightTag == NULL) { + return ILogicalBinaryComparator.Result.NULL; + } + if (!ATypeHierarchy.isCompatible(leftTag, rightTag)) { + return ILogicalBinaryComparator.Result.MISMATCH; + } + return null; + } + + // checking that left and right are compatible has to be done before calling this + public static ILogicalBinaryComparator.Result compareNumbers(ATypeTag leftTag, byte[] b1, int s1, ATypeTag rightTag, + byte[] b2, int s2) { + int result; + if (leftTag == DOUBLE || rightTag == DOUBLE) { + result = Double.compare(getValue(leftTag, b1, s1), getValue(rightTag, b2, s2)); + } else if (leftTag == FLOAT || rightTag == FLOAT) { + result = Float.compare((float) getValue(leftTag, b1, s1), (float) getValue(rightTag, b2, s2)); + } else if (leftTag == BIGINT || rightTag == BIGINT) { + result = Long.compare((long) getValue(leftTag, b1, s1), (long) getValue(rightTag, b2, s2)); + } else if (leftTag == INTEGER || leftTag == SMALLINT || leftTag == TINYINT) { + result = Integer.compare((int) getValue(leftTag, b1, s1), (int) getValue(rightTag, b2, s2)); + } else { + // two types that are compatible but are not numeric?? + return null; + } + return ILogicalBinaryComparator.returnResult(result); + } + + public static ILogicalBinaryComparator.Result compareNumWithConstant(ATypeTag leftTag, byte[] b1, int s1, + IAObject rightConstant) { + int result; + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + if (leftTag == DOUBLE || rightTag == DOUBLE) { + result = Double.compare(getValue(leftTag, b1, s1), getConstantValue(rightConstant)); + } else if (leftTag == FLOAT || rightTag == FLOAT) { + result = Float.compare((float) getValue(leftTag, b1, s1), (float) getConstantValue(rightConstant)); + } else if (leftTag == BIGINT || rightTag == BIGINT) { + result = Long.compare((long) getValue(leftTag, b1, s1), (long) getConstantValue(rightConstant)); + } else if (leftTag == INTEGER || leftTag == SMALLINT || leftTag == TINYINT) { + result = Integer.compare((int) getValue(leftTag, b1, s1), (int) getConstantValue(rightConstant)); + } else { + // two types that are compatible but are not numeric?? + return null; + } + return ILogicalBinaryComparator.returnResult(result); + } + + public static ILogicalBinaryComparator.Result compareConstants(IAObject leftConstant, IAObject rightConstant) { + int result; + ATypeTag leftTag = leftConstant.getType().getTypeTag(); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + if (leftTag == DOUBLE || rightTag == DOUBLE) { + result = Double.compare(getConstantValue(leftConstant), getConstantValue(rightConstant)); + } else if (leftTag == FLOAT || rightTag == FLOAT) { + result = Float.compare((float) getConstantValue(leftConstant), (float) getConstantValue(rightConstant)); + } else if (leftTag == BIGINT || rightTag == BIGINT) { + result = Long.compare((long) getConstantValue(leftConstant), (long) getConstantValue(rightConstant)); + } else if (leftTag == INTEGER || leftTag == SMALLINT || leftTag == TINYINT) { + result = Integer.compare((int) getConstantValue(leftConstant), (int) getConstantValue(rightConstant)); + } else { + // two types that are compatible but are not numeric?? + return null; + } + return ILogicalBinaryComparator.returnResult(result); + } + + private static double getValue(ATypeTag numericTag, byte[] b, int s) { + s++; + switch (numericTag) { + case TINYINT: + return AInt8SerializerDeserializer.getByte(b, s); + case SMALLINT: + return AInt16SerializerDeserializer.getShort(b, s); + case INTEGER: + return AInt32SerializerDeserializer.getInt(b, s); + case BIGINT: + return AInt64SerializerDeserializer.getLong(b, s); + case FLOAT: + return AFloatSerializerDeserializer.getFloat(b, s); + default: + return ADoubleSerializerDeserializer.getDouble(b, s); + } + } + + private static double getConstantValue(IAObject numeric) { + IAType type = numeric.getType(); + if (type == BuiltinType.ADOUBLE) { + return ((ADouble) numeric).getDoubleValue(); + } else if (type == BuiltinType.AFLOAT) { + return ((AFloat) numeric).getFloatValue(); + } else if (type == BuiltinType.AINT64) { + return ((AInt64) numeric).getLongValue(); + } else if (type == BuiltinType.AINT32) { + return ((AInt32) numeric).getIntegerValue(); + } else if (type == BuiltinType.AINT16) { + return ((AInt16) numeric).getShortValue(); + } else { + return ((AInt8) numeric).getByteValue(); + } + } +} diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalComplexBinaryComparator.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalComplexBinaryComparator.java new file mode 100644 index 0000000..3170608 --- /dev/null +++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalComplexBinaryComparator.java @@ -0,0 +1,98 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.asterix.dataflow.data.nontagged.comparators; + +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator; +import org.apache.asterix.dataflow.data.common.LogicalComparatorUtil; +import org.apache.asterix.om.base.IAObject; +import org.apache.asterix.om.types.ATypeTag; +import org.apache.asterix.om.types.EnumDeserializer; +import org.apache.asterix.om.types.IAType; +import org.apache.hyracks.api.exceptions.HyracksDataException; + +public class LogicalComplexBinaryComparator implements ILogicalBinaryComparator { + + private final IAType leftType; + private final IAType rightType; + private final LogicalScalarBinaryComparator scalarComparator = new LogicalScalarBinaryComparator(); + + public LogicalComplexBinaryComparator(IAType leftType, IAType rightType) { + this.leftType = leftType; + this.rightType = rightType; + } + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, byte[] rightBytes, int rightStart, int rightLen, + Operation operation) throws HyracksDataException { + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(rightBytes[rightStart]); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + if (!leftTag.isDerivedType() || !rightTag.isDerivedType()) { + return Result.NULL; + } + // TODO(ali): complex types(records, arrays, multisets) logic here + return Result.NULL; + } + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, IAObject rightConstant, Operation operation) { + // TODO(ali): not defined currently for constant complex types + if (rightConstant == null) { + return Result.NULL; + } + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + return Result.NULL; + } + + @Override + public Result compare(IAObject leftConstant, byte[] rightBytes, int rightStart, int rightLen, Operation operation) { + // TODO(ali): not defined currently for constant complex types + Result result = compare(rightBytes, rightStart, rightLen, leftConstant, operation); + if (result == Result.LT) { + return Result.GT; + } else if (result == Result.GT) { + return Result.LT; + } + return result; + } + + @Override + public Result compare(IAObject leftConstant, IAObject rightConstant, Operation operation) { + // TODO(ali): not defined currently for constant complex types + if (leftConstant == null || rightConstant == null) { + // illegal state maybe??? + return Result.NULL; + } + ATypeTag leftTag = leftConstant.getType().getTypeTag(); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + return Result.NULL; + } +} diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalGenericBinaryComparator.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalGenericBinaryComparator.java new file mode 100644 index 0000000..e3852b9 --- /dev/null +++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalGenericBinaryComparator.java @@ -0,0 +1,86 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.asterix.dataflow.data.nontagged.comparators; + +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator; +import org.apache.asterix.om.base.IAObject; +import org.apache.asterix.om.types.ATypeTag; +import org.apache.asterix.om.types.EnumDeserializer; +import org.apache.asterix.om.types.IAType; +import org.apache.hyracks.api.exceptions.HyracksDataException; + +public class LogicalGenericBinaryComparator implements ILogicalBinaryComparator { + + private final LogicalComplexBinaryComparator complexComparator; + private final LogicalScalarBinaryComparator scalarComparator = new LogicalScalarBinaryComparator(); + + public LogicalGenericBinaryComparator(IAType leftType, IAType rightType) { + complexComparator = new LogicalComplexBinaryComparator(leftType, rightType); + } + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, byte[] rightBytes, int rightStart, int rightLen, + Operation op) throws HyracksDataException { + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(rightBytes[rightStart]); + if (leftTag.isDerivedType() && rightTag.isDerivedType()) { + return complexComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen, op); + } + return scalarComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen, op); + } + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, IAObject rightConstant, Operation operation) { + if (rightConstant == null) { + // illegal state maybe??? + return Result.NULL; + } + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + if (leftTag.isDerivedType() && rightTag.isDerivedType()) { + return complexComparator.compare(leftBytes, leftStart, leftLen, rightConstant, operation); + } + return scalarComparator.compare(leftBytes, leftStart, leftLen, rightConstant, operation); + } + + @Override + public Result compare(IAObject leftConstant, byte[] rightBytes, int rightStart, int rightLen, Operation operation) { + Result result = compare(rightBytes, rightStart, rightLen, leftConstant, operation); + if (result == Result.LT) { + return Result.GT; + } else if (result == Result.GT) { + return Result.LT; + } + return result; + } + + @Override + public Result compare(IAObject leftConstant, IAObject rightConstant, Operation operation) { + if (leftConstant == null || rightConstant == null) { + // illegal state maybe??? + return Result.NULL; + } + ATypeTag leftTag = leftConstant.getType().getTypeTag(); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + if (leftTag.isDerivedType() && rightTag.isDerivedType()) { + return complexComparator.compare(leftConstant, rightConstant, operation); + } + return scalarComparator.compare(leftConstant, rightConstant, operation); + } +} diff --git a/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalScalarBinaryComparator.java b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalScalarBinaryComparator.java new file mode 100644 index 0000000..6387ecc --- /dev/null +++ b/asterixdb/asterix-om/src/main/java/org/apache/asterix/dataflow/data/nontagged/comparators/LogicalScalarBinaryComparator.java @@ -0,0 +1,221 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +package org.apache.asterix.dataflow.data.nontagged.comparators; + +import static org.apache.asterix.om.types.ATypeTag.CIRCLE; +import static org.apache.asterix.om.types.ATypeTag.DURATION; +import static org.apache.asterix.om.types.ATypeTag.INTERVAL; +import static org.apache.asterix.om.types.ATypeTag.LINE; +import static org.apache.asterix.om.types.ATypeTag.POINT; +import static org.apache.asterix.om.types.ATypeTag.POINT3D; +import static org.apache.asterix.om.types.ATypeTag.POLYGON; +import static org.apache.asterix.om.types.ATypeTag.RECTANGLE; + +import java.util.EnumSet; + +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator; +import org.apache.asterix.dataflow.data.common.LogicalComparatorUtil; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt32SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt64SerializerDeserializer; +import org.apache.asterix.formats.nontagged.BinaryComparatorFactoryProvider; +import org.apache.asterix.om.base.IAObject; +import org.apache.asterix.om.types.ATypeTag; +import org.apache.asterix.om.types.EnumDeserializer; +import org.apache.hyracks.api.dataflow.value.IBinaryComparator; +import org.apache.hyracks.api.exceptions.HyracksDataException; +import org.apache.hyracks.data.std.accessors.PointableBinaryComparatorFactory; +import org.apache.hyracks.data.std.primitive.ByteArrayPointable; + +public class LogicalScalarBinaryComparator implements ILogicalBinaryComparator { + + private final IBinaryComparator strBinaryComp = + BinaryComparatorFactoryProvider.UTF8STRING_POINTABLE_INSTANCE.createBinaryComparator(); + private final IBinaryComparator circleBinaryComp = + ACirclePartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator durationBinaryComp = + ADurationPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator intervalBinaryComp = + AIntervalAscPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator lineBinaryComparator = + ALinePartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator pointBinaryComparator = + APointPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator point3DBinaryComparator = + APoint3DPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator polygonBinaryComparator = + APolygonPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator rectangleBinaryComparator = + ARectanglePartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator uuidBinaryComparator = + AUUIDPartialBinaryComparatorFactory.INSTANCE.createBinaryComparator(); + private final IBinaryComparator byteArrayComparator = + new PointableBinaryComparatorFactory(ByteArrayPointable.FACTORY).createBinaryComparator(); + + private static final EnumSet<ATypeTag> UNDEFINED_TYPES = + EnumSet.of(DURATION, INTERVAL, LINE, POINT, POINT3D, POLYGON, CIRCLE, RECTANGLE); + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, byte[] rightBytes, int rightStart, int rightLen, + Operation operation) throws HyracksDataException { + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(rightBytes[rightStart]); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + if (comparisonUndefined(leftTag, rightTag, operation)) { + return Result.NULL; + } + // compare number if one of args is number + comparisonResult = + LogicalComparatorUtil.compareNumbers(leftTag, leftBytes, leftStart, rightTag, rightBytes, rightStart); + if (comparisonResult != null) { + return comparisonResult; + } + + // comparing non-numeric + // return null if !=, the assumption here is only numeric types are compatible with each other + if (leftTag != rightTag) { + return Result.NULL; + } + + leftStart++; + leftLen--; + rightStart++; + rightLen--; + + int result; + switch (leftTag) { + case BOOLEAN: + result = Integer.compare(leftBytes[leftStart], rightBytes[rightStart]); + break; + case STRING: + result = strBinaryComp.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case YEARMONTHDURATION: + case TIME: + case DATE: + result = Integer.compare(AInt32SerializerDeserializer.getInt(leftBytes, leftStart), + AInt32SerializerDeserializer.getInt(rightBytes, rightStart)); + break; + case DAYTIMEDURATION: + case DATETIME: + result = Long.compare(AInt64SerializerDeserializer.getLong(leftBytes, leftStart), + AInt64SerializerDeserializer.getLong(rightBytes, rightStart)); + break; + case CIRCLE: + result = circleBinaryComp.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case LINE: + result = lineBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case POINT: + result = pointBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case POINT3D: + result = point3DBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, + rightLen); + break; + case POLYGON: + result = polygonBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, + rightLen); + break; + case DURATION: + result = durationBinaryComp.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case INTERVAL: + result = intervalBinaryComp.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case RECTANGLE: + result = rectangleBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, + rightLen); + break; + case BINARY: + result = byteArrayComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + case UUID: + result = uuidBinaryComparator.compare(leftBytes, leftStart, leftLen, rightBytes, rightStart, rightLen); + break; + default: + return Result.NULL; + } + return ILogicalBinaryComparator.returnResult(result); + } + + @Override + public Result compare(byte[] leftBytes, int leftStart, int leftLen, IAObject rightConstant, Operation operation) { + // TODO(ali): currently defined for numbers only + if (rightConstant == null) { + return Result.NULL; + } + ATypeTag leftTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(leftBytes[leftStart]); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + if (comparisonUndefined(leftTag, rightTag, operation)) { + return Result.NULL; + } + comparisonResult = LogicalComparatorUtil.compareNumWithConstant(leftTag, leftBytes, leftStart, rightConstant); + if (comparisonResult != null) { + return comparisonResult; + } + return Result.NULL; + } + + @Override + public Result compare(IAObject leftConstant, byte[] rightBytes, int rightStart, int rightLen, Operation operation) { + // TODO(ali): currently defined for numbers only + Result result = compare(rightBytes, rightStart, rightLen, leftConstant, operation); + if (result == Result.LT) { + return Result.GT; + } else if (result == Result.GT) { + return Result.LT; + } + return result; + } + + @Override + public Result compare(IAObject leftConstant, IAObject rightConstant, Operation operation) { + // TODO(ali): currently defined for numbers only + if (leftConstant == null || rightConstant == null) { + // illegal state maybe??? + return Result.NULL; + } + ATypeTag leftTag = leftConstant.getType().getTypeTag(); + ATypeTag rightTag = rightConstant.getType().getTypeTag(); + Result comparisonResult = LogicalComparatorUtil.returnMissingOrNull(leftTag, rightTag); + if (comparisonResult != null) { + return comparisonResult; + } + if (comparisonUndefined(leftTag, rightTag, operation)) { + return Result.NULL; + } + comparisonResult = LogicalComparatorUtil.compareConstants(leftConstant, rightConstant); + if (comparisonResult != null) { + return comparisonResult; + } + return Result.NULL; + } + + private static boolean comparisonUndefined(ATypeTag leftTag, ATypeTag rightTag, Operation op) { + return op == Operation.INEQUALITY && (UNDEFINED_TYPES.contains(leftTag) || UNDEFINED_TYPES.contains(rightTag)); + } +} diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractComparisonEvaluator.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractComparisonEvaluator.java index 50e3932..89fd094 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractComparisonEvaluator.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractComparisonEvaluator.java @@ -20,50 +20,77 @@ import java.io.DataOutput; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; +import org.apache.asterix.dataflow.data.common.LogicalComparatorUtil; +import org.apache.asterix.dataflow.data.nontagged.serde.ADoubleSerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AFloatSerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt16SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt32SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt64SerializerDeserializer; +import org.apache.asterix.dataflow.data.nontagged.serde.AInt8SerializerDeserializer; +import org.apache.asterix.formats.nontagged.SerializerDeserializerProvider; +import org.apache.asterix.om.base.ADouble; +import org.apache.asterix.om.base.AFloat; +import org.apache.asterix.om.base.AInt16; +import org.apache.asterix.om.base.AInt32; +import org.apache.asterix.om.base.AInt64; +import org.apache.asterix.om.base.AInt8; +import org.apache.asterix.om.base.AMissing; +import org.apache.asterix.om.base.ANull; +import org.apache.asterix.om.base.IAObject; import org.apache.asterix.om.types.ATypeTag; +import org.apache.asterix.om.types.BuiltinType; import org.apache.asterix.om.types.EnumDeserializer; -import org.apache.asterix.om.types.hierachy.ATypeHierarchy; +import org.apache.asterix.om.types.IAType; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; import org.apache.hyracks.algebricks.runtime.evaluators.ConstantEvalFactory; import org.apache.hyracks.api.context.IHyracksTaskContext; +import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer; import org.apache.hyracks.api.exceptions.HyracksDataException; import org.apache.hyracks.api.exceptions.SourceLocation; import org.apache.hyracks.data.std.api.IPointable; import org.apache.hyracks.data.std.primitive.TaggedValuePointable; -import org.apache.hyracks.data.std.primitive.VoidPointable; import org.apache.hyracks.data.std.util.ArrayBackedValueStorage; import org.apache.hyracks.dataflow.common.data.accessors.IFrameTupleReference; public abstract class AbstractComparisonEvaluator implements IScalarEvaluator { + @SuppressWarnings("unchecked") + protected final ISerializerDeserializer<AMissing> missingSerde = + SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.AMISSING); + @SuppressWarnings("unchecked") + protected final ISerializerDeserializer<ANull> nullSerde = + SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.ANULL); protected final ArrayBackedValueStorage resultStorage = new ArrayBackedValueStorage(); protected final DataOutput out = resultStorage.getDataOutput(); protected final TaggedValuePointable argLeft = TaggedValuePointable.FACTORY.createPointable(); - protected final TaggedValuePointable argRight = TaggedValuePointable.FACTORY.createPointable(); - protected final IPointable outLeft = VoidPointable.FACTORY.createPointable(); - protected final IPointable outRight = VoidPointable.FACTORY.createPointable(); - protected final IScalarEvaluator evalLeft; - protected final IScalarEvaluator evalRight; + private final TaggedValuePointable argRight = TaggedValuePointable.FACTORY.createPointable(); + private final IScalarEvaluator evalLeft; + private final IScalarEvaluator evalRight; protected final SourceLocation sourceLoc; - private final ComparisonHelper ch; - private Number leftValue; - private Number rightValue; + private final ILogicalBinaryComparator logicalComparator; + private final Operation operation; + private IAObject leftConstant; + private IAObject rightConstant; - public AbstractComparisonEvaluator(IScalarEvaluatorFactory evalLeftFactory, - IScalarEvaluatorFactory evalRightFactory, IHyracksTaskContext ctx, SourceLocation sourceLoc) - throws HyracksDataException { + public AbstractComparisonEvaluator(IScalarEvaluatorFactory evalLeftFactory, IAType leftType, + IScalarEvaluatorFactory evalRightFactory, IAType rightType, IHyracksTaskContext ctx, + SourceLocation sourceLoc, Operation operation) throws HyracksDataException { this.evalLeft = evalLeftFactory.createScalarEvaluator(ctx); this.evalRight = evalRightFactory.createScalarEvaluator(ctx); this.sourceLoc = sourceLoc; - ch = new ComparisonHelper(sourceLoc); - leftValue = getValueOfConstantEval(evalLeftFactory); - rightValue = getValueOfConstantEval(evalRightFactory); + this.operation = operation; + logicalComparator = LogicalComparatorUtil.createLogicalComparator(leftType, rightType); + leftConstant = getValueOfConstantEval(evalLeftFactory); + rightConstant = getValueOfConstantEval(evalRightFactory); } - private Number getValueOfConstantEval(IScalarEvaluatorFactory factory) throws HyracksDataException { + private IAObject getValueOfConstantEval(IScalarEvaluatorFactory factory) { if (factory instanceof ConstantEvalFactory) { - return ch.getNumberValue(((ConstantEvalFactory) factory).getValue()); + return getConstantValue(((ConstantEvalFactory) factory).getValue()); } return null; } @@ -73,27 +100,63 @@ // Evaluates input args. evalLeft.evaluate(tuple, argLeft); evalRight.evaluate(tuple, argRight); - argLeft.getValue(outLeft); - argRight.getValue(outRight); - evaluateImpl(result); } protected abstract void evaluateImpl(IPointable result) throws HyracksDataException; - // checks whether two types are comparable - boolean comparabilityCheck() { - // Checks whether two types are comparable or not - ATypeTag typeTag1 = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(argLeft.getTag()); - ATypeTag typeTag2 = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(argRight.getTag()); - - // Are two types compatible, meaning that they can be compared? (e.g., compare between numeric types - return ATypeHierarchy.isCompatible(typeTag1, typeTag2); + Result compare() throws HyracksDataException { + if (leftConstant != null && rightConstant != null) { + // both are constants + return logicalComparator.compare(leftConstant, rightConstant, operation); + } else if (leftConstant != null) { + // left is constant, right isn't + return logicalComparator.compare(leftConstant, argRight.getByteArray(), argRight.getStartOffset(), + argRight.getLength(), operation); + } else if (rightConstant != null) { + // right is constant, left isn't + return logicalComparator.compare(argLeft.getByteArray(), argLeft.getStartOffset(), argLeft.getLength(), + rightConstant, operation); + } else { + return logicalComparator.compare(argLeft.getByteArray(), argLeft.getStartOffset(), argLeft.getLength(), + argRight.getByteArray(), argRight.getStartOffset(), argRight.getLength(), operation); + } } - int compare() throws HyracksDataException { - ATypeTag leftTypeTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(argLeft.getTag()); - ATypeTag rightTypeTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(argRight.getTag()); - return ch.compare(leftTypeTag, rightTypeTag, outLeft, outRight, leftValue, rightValue); + void writeMissing(IPointable result) throws HyracksDataException { + resultStorage.reset(); + missingSerde.serialize(AMissing.MISSING, out); + result.set(resultStorage); + } + + void writeNull(IPointable result) throws HyracksDataException { + resultStorage.reset(); + nullSerde.serialize(ANull.NULL, out); + result.set(resultStorage); + } + + private IAObject getConstantValue(byte[] bytes) { + int start = 0; + ATypeTag typeTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(bytes[start]); + if (typeTag == null) { + return null; + } + start++; + switch (typeTag) { + case TINYINT: + return new AInt8(AInt8SerializerDeserializer.getByte(bytes, start)); + case SMALLINT: + return new AInt16(AInt16SerializerDeserializer.getShort(bytes, start)); + case INTEGER: + return new AInt32(AInt32SerializerDeserializer.getInt(bytes, start)); + case BIGINT: + return new AInt64(AInt64SerializerDeserializer.getLong(bytes, start)); + case FLOAT: + return new AFloat(AFloatSerializerDeserializer.getFloat(bytes, start)); + case DOUBLE: + return new ADouble(ADoubleSerializerDeserializer.getDouble(bytes, start)); + default: + return null; + } } } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractIfEqualsEvaluator.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractIfEqualsEvaluator.java index 27ae471..40c5ab9 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractIfEqualsEvaluator.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractIfEqualsEvaluator.java @@ -19,6 +19,9 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; +import org.apache.asterix.om.types.IAType; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; import org.apache.hyracks.api.context.IHyracksTaskContext; import org.apache.hyracks.api.exceptions.HyracksDataException; @@ -27,14 +30,20 @@ public abstract class AbstractIfEqualsEvaluator extends AbstractComparisonEvaluator { - AbstractIfEqualsEvaluator(IScalarEvaluatorFactory evalLeftFactory, IScalarEvaluatorFactory evalRightFactory, - IHyracksTaskContext ctx, SourceLocation sourceLoc) throws HyracksDataException { - super(evalLeftFactory, evalRightFactory, ctx, sourceLoc); + AbstractIfEqualsEvaluator(IScalarEvaluatorFactory evalLeftFactory, IAType leftType, + IScalarEvaluatorFactory evalRightFactory, IAType rightType, IHyracksTaskContext ctx, + SourceLocation sourceLoc) throws HyracksDataException { + super(evalLeftFactory, leftType, evalRightFactory, rightType, ctx, sourceLoc, Operation.EQUALITY); } @Override protected void evaluateImpl(IPointable result) throws HyracksDataException { - if (comparabilityCheck() && compare() == 0) { + Result comparisonResult = compare(); + if (comparisonResult == Result.MISSING) { + writeMissing(result); + } else if (comparisonResult == Result.NULL) { + writeNull(result); + } else if (comparisonResult == Result.EQ) { resultStorage.reset(); writeEqualsResult(); result.set(resultStorage); diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractValueComparisonEvaluator.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractValueComparisonEvaluator.java index 2d8c499..5b27ed8 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractValueComparisonEvaluator.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/AbstractValueComparisonEvaluator.java @@ -19,13 +19,12 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.formats.nontagged.SerializerDeserializerProvider; import org.apache.asterix.om.base.ABoolean; -import org.apache.asterix.om.base.ANull; -import org.apache.asterix.om.types.ATypeTag; import org.apache.asterix.om.types.BuiltinType; -import org.apache.asterix.om.types.EnumDeserializer; -import org.apache.asterix.runtime.exceptions.UnsupportedTypeException; +import org.apache.asterix.om.types.IAType; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; import org.apache.hyracks.api.context.IHyracksTaskContext; import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer; @@ -35,64 +34,29 @@ public abstract class AbstractValueComparisonEvaluator extends AbstractComparisonEvaluator { @SuppressWarnings("unchecked") - protected ISerializerDeserializer<ABoolean> serde = + private ISerializerDeserializer<ABoolean> serde = SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.ABOOLEAN); - @SuppressWarnings("unchecked") - protected ISerializerDeserializer<ANull> nullSerde = - SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.ANULL); - public AbstractValueComparisonEvaluator(IScalarEvaluatorFactory evalLeftFactory, - IScalarEvaluatorFactory evalRightFactory, IHyracksTaskContext ctx, SourceLocation sourceLoc) - throws HyracksDataException { - super(evalLeftFactory, evalRightFactory, ctx, sourceLoc); + public AbstractValueComparisonEvaluator(IScalarEvaluatorFactory evalLeftFactory, IAType leftType, + IScalarEvaluatorFactory evalRightFactory, IAType rightType, IHyracksTaskContext ctx, + SourceLocation sourceLoc, Operation operation) throws HyracksDataException { + super(evalLeftFactory, leftType, evalRightFactory, rightType, ctx, sourceLoc, operation); } @Override protected void evaluateImpl(IPointable result) throws HyracksDataException { - resultStorage.reset(); - - // checks whether we can apply >, >=, <, and <= to the given type since - // these operations cannot be defined for certain types. - if (isTotallyOrderable()) { - checkTotallyOrderable(); - } - - // Checks whether two types are comparable - if (comparabilityCheck()) { - // Two types can be compared - int r = compare(); - ABoolean b = getComparisonResult(r) ? ABoolean.TRUE : ABoolean.FALSE; - serde.serialize(b, out); + Result comparisonResult = compare(); + if (comparisonResult == Result.MISSING) { + writeMissing(result); + } else if (comparisonResult == Result.NULL || comparisonResult == Result.MISMATCH) { + writeNull(result); } else { - // result:NULL - two types cannot be compared. - nullSerde.serialize(ANull.NULL, out); - } - result.set(resultStorage); - } - - protected abstract boolean isTotallyOrderable(); - - protected abstract boolean getComparisonResult(int r); - - // checks whether we can apply >, >=, <, and <= operations to the given type since - // these operations can not be defined for certain types. - protected void checkTotallyOrderable() throws HyracksDataException { - if (argLeft.getLength() != 0) { - ATypeTag typeTag = EnumDeserializer.ATYPETAGDESERIALIZER.deserialize(argLeft.getTag()); - switch (typeTag) { - case DURATION: - case INTERVAL: - case LINE: - case POINT: - case POINT3D: - case POLYGON: - case CIRCLE: - case RECTANGLE: - throw new UnsupportedTypeException(sourceLoc, ComparisonHelper.COMPARISON, argLeft.getTag()); - default: - return; - } + resultStorage.reset(); + ABoolean b = getComparisonResult(comparisonResult) ? ABoolean.TRUE : ABoolean.FALSE; + serde.serialize(b, out); + result.set(resultStorage); } } + protected abstract boolean getComparisonResult(Result r); } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/EqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/EqualsDescriptor.java index f38c3e5..e97c313 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/EqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/EqualsDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class EqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new EqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.EQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r == 0; - } - - @Override - protected boolean isTotallyOrderable() { - return false; + protected boolean getComparisonResult(Result r) { + return r == Result.EQ; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanDescriptor.java index 3815666..b5095f6 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class GreaterThanDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new GreaterThanDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.INEQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r > 0; - } - - @Override - protected boolean isTotallyOrderable() { - return true; + protected boolean getComparisonResult(Result r) { + return r == Result.GT; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanOrEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanOrEqualsDescriptor.java index 1598165..7083292 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanOrEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/GreaterThanOrEqualsDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class GreaterThanOrEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new GreaterThanOrEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.INEQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r >= 0; - } - - @Override - protected boolean isTotallyOrderable() { - return true; + protected boolean getComparisonResult(Result r) { + return r == Result.GT || r == Result.EQ; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanDescriptor.java index 4198934..751aa0f 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class LessThanDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new LessThanDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.INEQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r < 0; - } - - @Override - protected boolean isTotallyOrderable() { - return true; + protected boolean getComparisonResult(Result r) { + return r == Result.LT; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanOrEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanOrEqualsDescriptor.java index 478c652..bb5deca 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanOrEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/LessThanOrEqualsDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class LessThanOrEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new LessThanOrEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.INEQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r <= 0; - } - - @Override - protected boolean isTotallyOrderable() { - return true; + protected boolean getComparisonResult(Result r) { + return r == Result.LT || r == Result.EQ; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/MissingIfEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/MissingIfEqualsDescriptor.java index 7ed194c..13c87f4 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/MissingIfEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/MissingIfEqualsDescriptor.java @@ -19,26 +19,34 @@ package org.apache.asterix.runtime.evaluators.comparisons; -import org.apache.asterix.formats.nontagged.SerializerDeserializerProvider; import org.apache.asterix.om.base.AMissing; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; -import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; import org.apache.hyracks.api.context.IHyracksTaskContext; -import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer; import org.apache.hyracks.api.exceptions.HyracksDataException; public class MissingIfEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new MissingIfEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -48,17 +56,19 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractIfEqualsEvaluator(args[0], args[1], ctx, sourceLoc) { - - @SuppressWarnings("unchecked") - final ISerializerDeserializer<AMissing> missingSerde = - SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.AMISSING); + return new AbstractIfEqualsEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc) { @Override protected void writeEqualsResult() throws HyracksDataException { diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NanIfEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NanIfEqualsDescriptor.java index af50678..9d25858 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NanIfEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NanIfEqualsDescriptor.java @@ -25,8 +25,11 @@ import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -36,10 +39,18 @@ public class NanIfEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new NanIfEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -49,13 +60,19 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractIfEqualsEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractIfEqualsEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc) { final AMutableDouble equalsResult = new AMutableDouble(Double.NaN); diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NegInfIfEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NegInfIfEqualsDescriptor.java index a70bc7b..d77cd4c 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NegInfIfEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NegInfIfEqualsDescriptor.java @@ -25,8 +25,11 @@ import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -36,10 +39,18 @@ public class NegInfIfEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new NegInfIfEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -49,13 +60,19 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractIfEqualsEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractIfEqualsEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc) { final AMutableDouble equalsResult = new AMutableDouble(Double.NEGATIVE_INFINITY); diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NotEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NotEqualsDescriptor.java index 6e03ef8..5216869 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NotEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NotEqualsDescriptor.java @@ -19,10 +19,15 @@ package org.apache.asterix.runtime.evaluators.comparisons; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Operation; +import org.apache.asterix.dataflow.data.common.ILogicalBinaryComparator.Result; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -31,10 +36,18 @@ public class NotEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new NotEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -44,22 +57,24 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractValueComparisonEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractValueComparisonEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc, + Operation.EQUALITY) { @Override - protected boolean getComparisonResult(int r) { - return r != 0; - } - - @Override - protected boolean isTotallyOrderable() { - return false; + protected boolean getComparisonResult(Result r) { + return r != Result.EQ; } }; } diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NullIfEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NullIfEqualsDescriptor.java index 5df5142..d990831 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NullIfEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/NullIfEqualsDescriptor.java @@ -19,26 +19,34 @@ package org.apache.asterix.runtime.evaluators.comparisons; -import org.apache.asterix.formats.nontagged.SerializerDeserializerProvider; import org.apache.asterix.om.base.ANull; import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; -import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.functions.IFunctionTypeInferer; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; import org.apache.hyracks.api.context.IHyracksTaskContext; -import org.apache.hyracks.api.dataflow.value.ISerializerDeserializer; import org.apache.hyracks.api.exceptions.HyracksDataException; public class NullIfEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new NullIfEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -48,17 +56,19 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractIfEqualsEvaluator(args[0], args[1], ctx, sourceLoc) { - - @SuppressWarnings("unchecked") - final ISerializerDeserializer<ANull> nullSerde = - SerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(BuiltinType.ANULL); + return new AbstractIfEqualsEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc) { @Override protected void writeEqualsResult() throws HyracksDataException { diff --git a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/PosInfIfEqualsDescriptor.java b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/PosInfIfEqualsDescriptor.java index a1f4f13..52c41bb 100644 --- a/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/PosInfIfEqualsDescriptor.java +++ b/asterixdb/asterix-runtime/src/main/java/org/apache/asterix/runtime/evaluators/comparisons/PosInfIfEqualsDescriptor.java @@ -25,8 +25,11 @@ import org.apache.asterix.om.functions.BuiltinFunctions; import org.apache.asterix.om.functions.IFunctionDescriptor; import org.apache.asterix.om.functions.IFunctionDescriptorFactory; +import org.apache.asterix.om.functions.IFunctionTypeInferer; import org.apache.asterix.om.types.BuiltinType; +import org.apache.asterix.om.types.IAType; import org.apache.asterix.runtime.evaluators.base.AbstractScalarFunctionDynamicDescriptor; +import org.apache.asterix.runtime.functions.FunctionTypeInferers; import org.apache.hyracks.algebricks.core.algebra.functions.FunctionIdentifier; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluator; import org.apache.hyracks.algebricks.runtime.base.IScalarEvaluatorFactory; @@ -36,10 +39,18 @@ public class PosInfIfEqualsDescriptor extends AbstractScalarFunctionDynamicDescriptor { private static final long serialVersionUID = 1L; + private IAType leftType; + private IAType rightType; + public static final IFunctionDescriptorFactory FACTORY = new IFunctionDescriptorFactory() { @Override public IFunctionDescriptor createFunctionDescriptor() { return new PosInfIfEqualsDescriptor(); + } + + @Override + public IFunctionTypeInferer createFunctionTypeInferer() { + return FunctionTypeInferers.SET_ARGUMENTS_TYPE; } }; @@ -49,13 +60,19 @@ } @Override + public void setImmutableStates(Object... types) { + leftType = (IAType) types[0]; + rightType = (IAType) types[1]; + } + + @Override public IScalarEvaluatorFactory createEvaluatorFactory(IScalarEvaluatorFactory[] args) { return new IScalarEvaluatorFactory() { private static final long serialVersionUID = 1L; @Override public IScalarEvaluator createScalarEvaluator(IHyracksTaskContext ctx) throws HyracksDataException { - return new AbstractIfEqualsEvaluator(args[0], args[1], ctx, sourceLoc) { + return new AbstractIfEqualsEvaluator(args[0], leftType, args[1], rightType, ctx, sourceLoc) { final AMutableDouble equalsResult = new AMutableDouble(Double.POSITIVE_INFINITY); -- To view, visit https://asterix-gerrit.ics.uci.edu/3145 To unsubscribe, visit https://asterix-gerrit.ics.uci.edu/settings Gerrit-MessageType: newchange Gerrit-Change-Id: I623662861e6f3b1fdcff78f8edc0e3216ca10fe1 Gerrit-PatchSet: 1 Gerrit-Project: asterixdb Gerrit-Branch: master Gerrit-Owner: Ali Alsuliman <ali.al.solai...@gmail.com>