Repository: beam Updated Branches: refs/heads/DSL_SQL 2f8ee9884 -> 4c47ba00b
[BEAM-2384] CEIL, FLOOR, TRUNCATE, PI, ATAN2 math functions Project: http://git-wip-us.apache.org/repos/asf/beam/repo Commit: http://git-wip-us.apache.org/repos/asf/beam/commit/caa9450a Tree: http://git-wip-us.apache.org/repos/asf/beam/tree/caa9450a Diff: http://git-wip-us.apache.org/repos/asf/beam/diff/caa9450a Branch: refs/heads/DSL_SQL Commit: caa9450a618e882ecfbf3f28f9bc2d5dacb88ea7 Parents: 2f8ee98 Author: tarushapptech <tarushappt...@gmail.com> Authored: Thu Jul 6 17:16:19 2017 +0530 Committer: JingsongLi <lzljs3620...@aliyun.com> Committed: Tue Jul 18 14:55:27 2017 +0800 ---------------------------------------------------------------------- .../dsls/sql/interpreter/BeamSqlFnExecutor.java | 26 +++++++- .../operator/math/BeamSqlAtan2Expression.java | 44 +++++++++++++ .../operator/math/BeamSqlCeilExpression.java | 47 ++++++++++++++ .../operator/math/BeamSqlFloorExpression.java | 47 ++++++++++++++ .../operator/math/BeamSqlPiExpression.java | 42 +++++++++++++ .../math/BeamSqlTruncateExpression.java | 66 ++++++++++++++++++++ .../math/BeamSqlMathBinaryExpressionTest.java | 20 ++++++ .../math/BeamSqlMathUnaryExpressionTest.java | 18 ++++++ 8 files changed, 308 insertions(+), 2 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/BeamSqlFnExecutor.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/BeamSqlFnExecutor.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/BeamSqlFnExecutor.java index de4112d..e505825 100644 --- a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/BeamSqlFnExecutor.java +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/BeamSqlFnExecutor.java @@ -57,12 +57,16 @@ import org.apache.beam.dsls.sql.interpreter.operator.logical.BeamSqlOrExpression import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlAbsExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlAcosExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlAsinExpression; +import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlAtan2Expression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlAtanExpression; +import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlCeilExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlCotExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlDegreesExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlExpExpression; +import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlFloorExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlLnExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlLogExpression; +import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlPiExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlPowerExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlRadiansExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlRoundExpression; @@ -70,6 +74,7 @@ import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlSignExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlSinExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlSqrtExpression; import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlTanExpression; +import org.apache.beam.dsls.sql.interpreter.operator.math.BeamSqlTruncateExpression; import org.apache.beam.dsls.sql.interpreter.operator.string.BeamSqlCharLengthExpression; import org.apache.beam.dsls.sql.interpreter.operator.string.BeamSqlConcatExpression; import org.apache.beam.dsls.sql.interpreter.operator.string.BeamSqlInitCapExpression; @@ -286,6 +291,15 @@ public class BeamSqlFnExecutor implements BeamSqlExpressionExecutor { case "POWER": ret = new BeamSqlPowerExpression(subExps); break; + case "PI": + ret = new BeamSqlPiExpression(); + break; + case "ATAN2": + ret = new BeamSqlAtan2Expression(subExps); + break; + case "TRUNCATE": + ret = new BeamSqlTruncateExpression(subExps); + break; // string operators case "||": @@ -321,9 +335,17 @@ public class BeamSqlFnExecutor implements BeamSqlExpressionExecutor { case "REINTERPRET": return new BeamSqlReinterpretExpression(subExps, node.type.getSqlTypeName()); case "CEIL": - return new BeamSqlDateCeilExpression(subExps); + if (SqlTypeName.NUMERIC_TYPES.contains(node.type.getSqlTypeName())) { + return new BeamSqlCeilExpression(subExps); + } else { + return new BeamSqlDateCeilExpression(subExps); + } case "FLOOR": - return new BeamSqlDateFloorExpression(subExps); + if (SqlTypeName.NUMERIC_TYPES.contains(node.type.getSqlTypeName())) { + return new BeamSqlFloorExpression(subExps); + } else { + return new BeamSqlDateFloorExpression(subExps); + } case "EXTRACT_DATE": case "EXTRACT": return new BeamSqlExtractExpression(subExps); http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlAtan2Expression.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlAtan2Expression.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlAtan2Expression.java new file mode 100644 index 0000000..c71ca9d --- /dev/null +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlAtan2Expression.java @@ -0,0 +1,44 @@ +/* + * 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.beam.dsls.sql.interpreter.operator.math; + +import java.util.List; + +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlExpression; +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlPrimitive; +import org.apache.calcite.runtime.SqlFunctions; +import org.apache.calcite.sql.type.SqlTypeName; + +/** + * {@link BeamSqlMathBinaryExpression} for 'ATAN2' function. + */ +public class BeamSqlAtan2Expression extends BeamSqlMathBinaryExpression { + + public BeamSqlAtan2Expression(List<BeamSqlExpression> operands) { + super(operands); + this.outputType = SqlTypeName.DOUBLE; + } + + @Override public BeamSqlPrimitive<? extends Number> calculate(BeamSqlPrimitive leftOp, + BeamSqlPrimitive rightOp) { + return BeamSqlPrimitive.of(SqlTypeName.DOUBLE, SqlFunctions + .atan2(SqlFunctions.toDouble(leftOp.getValue()), + SqlFunctions.toDouble(rightOp.getValue()))); + } +} http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlCeilExpression.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlCeilExpression.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlCeilExpression.java new file mode 100644 index 0000000..c035a75 --- /dev/null +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlCeilExpression.java @@ -0,0 +1,47 @@ +/* + * 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.beam.dsls.sql.interpreter.operator.math; + +import java.util.List; + +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlExpression; +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlPrimitive; +import org.apache.calcite.runtime.SqlFunctions; +import org.apache.calcite.sql.type.SqlTypeName; + +/** + * {@code BeamSqlMathUnaryExpression} for 'CEIL' function. + */ +public class BeamSqlCeilExpression extends BeamSqlMathUnaryExpression { + + public BeamSqlCeilExpression(List<BeamSqlExpression> operands) { + super(operands); + this.outputType = SqlTypeName.DOUBLE; + } + + @Override public BeamSqlPrimitive calculate(BeamSqlPrimitive op) { + switch (getOutputType()) { + case DECIMAL: + return BeamSqlPrimitive.of(SqlTypeName.DECIMAL, SqlFunctions.ceil(op.getDecimal())); + default: + return BeamSqlPrimitive + .of(SqlTypeName.DOUBLE, SqlFunctions.ceil(SqlFunctions.toDouble(op.getValue()))); + } + } +} http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlFloorExpression.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlFloorExpression.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlFloorExpression.java new file mode 100644 index 0000000..fe18927 --- /dev/null +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlFloorExpression.java @@ -0,0 +1,47 @@ +/* + * 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.beam.dsls.sql.interpreter.operator.math; + +import java.util.List; + +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlExpression; +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlPrimitive; +import org.apache.calcite.runtime.SqlFunctions; +import org.apache.calcite.sql.type.SqlTypeName; + +/** + * {@code BeamSqlMathUnaryExpression} for 'FLOOR' function. + */ +public class BeamSqlFloorExpression extends BeamSqlMathUnaryExpression { + + public BeamSqlFloorExpression(List<BeamSqlExpression> operands) { + super(operands); + this.outputType = SqlTypeName.DOUBLE; + } + + @Override public BeamSqlPrimitive calculate(BeamSqlPrimitive op) { + switch (getOutputType()) { + case DECIMAL: + return BeamSqlPrimitive.of(SqlTypeName.DECIMAL, SqlFunctions.floor(op.getDecimal())); + default: + return BeamSqlPrimitive + .of(SqlTypeName.DOUBLE, SqlFunctions.floor(SqlFunctions.toDouble(op.getValue()))); + } + } +} http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlPiExpression.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlPiExpression.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlPiExpression.java new file mode 100644 index 0000000..4645951 --- /dev/null +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlPiExpression.java @@ -0,0 +1,42 @@ +/* + * 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.beam.dsls.sql.interpreter.operator.math; + +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlExpression; +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlPrimitive; +import org.apache.beam.dsls.sql.schema.BeamSqlRow; +import org.apache.calcite.sql.type.SqlTypeName; + +/** + * Base class for the PI function. + */ +public class BeamSqlPiExpression extends BeamSqlExpression { + + public BeamSqlPiExpression() { + this.outputType = SqlTypeName.DOUBLE; + } + + @Override public boolean accept() { + return numberOfOperands() == 0; + } + + @Override public BeamSqlPrimitive evaluate(BeamSqlRow inputRecord) { + return BeamSqlPrimitive.of(SqlTypeName.DOUBLE, Math.PI); + } +} http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlTruncateExpression.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlTruncateExpression.java b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlTruncateExpression.java new file mode 100644 index 0000000..a123bf7 --- /dev/null +++ b/dsls/sql/src/main/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlTruncateExpression.java @@ -0,0 +1,66 @@ +/* + * 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.beam.dsls.sql.interpreter.operator.math; + +import java.util.List; + +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlExpression; +import org.apache.beam.dsls.sql.interpreter.operator.BeamSqlPrimitive; +import org.apache.calcite.runtime.SqlFunctions; +import org.apache.calcite.sql.type.SqlTypeName; + +/** + * {@code BeamSqlMathBinaryExpression} for 'TRUNCATE' function. + */ +public class BeamSqlTruncateExpression extends BeamSqlMathBinaryExpression { + + public BeamSqlTruncateExpression(List<BeamSqlExpression> operands) { + super(operands); + } + + @Override public BeamSqlPrimitive<? extends Number> calculate(BeamSqlPrimitive leftOp, + BeamSqlPrimitive rightOp) { + BeamSqlPrimitive result = null; + int rightIntOperand = SqlFunctions.toInt(rightOp.getValue()); + switch (leftOp.getOutputType()) { + case SMALLINT: + case TINYINT: + case INTEGER: + result = BeamSqlPrimitive.of(SqlTypeName.INTEGER, + SqlFunctions.struncate(SqlFunctions.toInt(leftOp.getValue()), rightIntOperand)); + break; + case BIGINT: + result = BeamSqlPrimitive + .of(SqlTypeName.BIGINT, SqlFunctions.struncate(leftOp.getLong(), rightIntOperand)); + break; + case FLOAT: + case DOUBLE: + result = BeamSqlPrimitive.of(SqlTypeName.DOUBLE, + SqlFunctions.struncate(SqlFunctions.toDouble(leftOp.getValue()), rightIntOperand)); + break; + case DECIMAL: + result = BeamSqlPrimitive + .of(SqlTypeName.DECIMAL, SqlFunctions.struncate(leftOp.getDecimal(), rightIntOperand)); + break; + default: + break; + } + return result; + } +} http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathBinaryExpressionTest.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathBinaryExpressionTest.java b/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathBinaryExpressionTest.java index 143b9da..ddb27a9 100644 --- a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathBinaryExpressionTest.java +++ b/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathBinaryExpressionTest.java @@ -180,4 +180,24 @@ public class BeamSqlMathBinaryExpressionTest extends BeamSqlFnExecutorTestBase { new BeamSqlPowerExpression(operands).evaluate(record).getValue()); } + @Test public void testForTruncate() { + List<BeamSqlExpression> operands = new ArrayList<>(); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 2.0)); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 4.0)); + assertEquals(2.0, new BeamSqlTruncateExpression(operands).evaluate(record).getValue()); + // truncate(double, integer) => double + operands.clear(); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 2.80685)); + operands.add(BeamSqlPrimitive.of(SqlTypeName.INTEGER, 4)); + assertEquals(2.8068, new BeamSqlTruncateExpression(operands).evaluate(record).getValue()); + } + + @Test public void testForAtan2() { + List<BeamSqlExpression> operands = new ArrayList<>(); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 0.875)); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 0.56)); + assertEquals(Math.atan2(0.875, 0.56), + new BeamSqlAtan2Expression(operands).evaluate(record).getValue()); + } + } http://git-wip-us.apache.org/repos/asf/beam/blob/caa9450a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathUnaryExpressionTest.java ---------------------------------------------------------------------- diff --git a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathUnaryExpressionTest.java b/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathUnaryExpressionTest.java index 38f5db6..510c65e 100644 --- a/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathUnaryExpressionTest.java +++ b/dsls/sql/src/test/java/org/apache/beam/dsls/sql/interpreter/operator/math/BeamSqlMathUnaryExpressionTest.java @@ -293,4 +293,22 @@ public class BeamSqlMathUnaryExpressionTest extends BeamSqlFnExecutorTestBase { new BeamSqlSignExpression(operands).evaluate(record).getValue()); } + @Test public void testForPi() { + Assert.assertEquals(Math.PI, new BeamSqlPiExpression().evaluate(record).getValue()); + } + + @Test public void testForCeil() { + List<BeamSqlExpression> operands = new ArrayList<>(); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 2.68687979)); + Assert.assertEquals(Math.ceil(2.68687979), + new BeamSqlCeilExpression(operands).evaluate(record).getValue()); + } + + @Test public void testForFloor() { + List<BeamSqlExpression> operands = new ArrayList<>(); + operands.add(BeamSqlPrimitive.of(SqlTypeName.DOUBLE, 2.68687979)); + Assert.assertEquals(Math.floor(2.68687979), + new BeamSqlFloorExpression(operands).evaluate(record).getValue()); + } + }