未验证 提交 6767dfe4 编写于 作者: V Vlad Ilyushchenko 提交者: GitHub

feat(sql): bitwise ops implementation (#1046)

上级 3cb01d42
......@@ -679,7 +679,7 @@ class ExpressionParser {
int operatorType = op.type;
if (thisChar == '-') {
if (thisChar == '-' || thisChar == '~') {
switch (prevBranch) {
case BRANCH_OPERATOR:
case BRANCH_LEFT_BRACE:
......
......@@ -37,7 +37,6 @@ public final class OperatorExpression {
static final ObjList<OperatorExpression> operators = new ObjList<OperatorExpression>() {{
add(new OperatorExpression(".", DOT_PRECEDENCE, false, BINARY));
add(new OperatorExpression("::", DOT_PRECEDENCE, false, BINARY));
add(new OperatorExpression("^", 2, false, BINARY));
add(new OperatorExpression("*", 3, true, BINARY));
add(new OperatorExpression("/", 3, true, BINARY));
add(new OperatorExpression("%", 3, true, BINARY));
......@@ -55,6 +54,9 @@ public final class OperatorExpression {
add(new OperatorExpression("!~", 7, true, BINARY));
add(new OperatorExpression("in", 7, true, SET, false));
add(new OperatorExpression("between", 7, true, SET, false));
add(new OperatorExpression("&", 8, true, BINARY));
add(new OperatorExpression("^", 9, false, BINARY));
add(new OperatorExpression("|", 10, true, BINARY));
add(new OperatorExpression("and", 11, true, BINARY, false));
add(new OperatorExpression("or", 11, true, BINARY, false));
add(new OperatorExpression("not", 11, true, UNARY, false));
......
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.IntFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseAndIntFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "&(II)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitAndIntFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitAndIntFunction extends IntFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitAndIntFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public int getInt(Record rec) {
final int l = left.getInt(rec);
final int r = right.getInt(rec);
return l != Numbers.INT_NaN && r != Numbers.INT_NaN ? l & r : Numbers.INT_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.LongFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseAndLongFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "&(LL)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitAndLongFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitAndLongFunction extends LongFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitAndLongFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public long getLong(Record rec) {
final long l = left.getLong(rec);
final long r = right.getLong(rec);
return l != Numbers.LONG_NaN && r != Numbers.LONG_NaN ? l & r : Numbers.LONG_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.IntFunction;
import io.questdb.griffin.engine.functions.UnaryFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseNotIntFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "~(I)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitNotIntFunction(position, args.getQuick(0));
}
public static final class BitNotIntFunction extends IntFunction implements UnaryFunction {
private final Function value;
public BitNotIntFunction(int position, Function value) {
super(position);
this.value = value;
}
@Override
public Function getArg() {
return value;
}
@Override
public int getInt(Record rec) {
final int val = value.getInt(rec);
return val != Numbers.INT_NaN ? ~val : Numbers.INT_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.LongFunction;
import io.questdb.griffin.engine.functions.UnaryFunction;
import io.questdb.griffin.engine.functions.constants.LongConstant;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseNotLongFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "~(L)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitNotLongFunction(position, args.getQuick(0));
}
public static final class BitNotLongFunction extends LongFunction implements UnaryFunction {
private final Function value;
public BitNotLongFunction(int position, Function value) {
super(position);
this.value = value;
}
@Override
public Function getArg() {
return value;
}
@Override
public long getLong(Record rec) {
final long val = value.getLong(rec);
return val != Numbers.LONG_NaN ? ~val : Numbers.LONG_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.IntFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseOrIntFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "|(II)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitOrIntFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitOrIntFunction extends IntFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitOrIntFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public int getInt(Record rec) {
final int l = left.getInt(rec);
final int r = right.getInt(rec);
return l != Numbers.INT_NaN && r != Numbers.INT_NaN ? l | r : Numbers.INT_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.LongFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseOrLongFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "|(LL)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitOrLongFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitOrLongFunction extends LongFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitOrLongFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public long getLong(Record rec) {
final long l = left.getLong(rec);
final long r = right.getLong(rec);
return l != Numbers.LONG_NaN && r != Numbers.LONG_NaN ? l | r : Numbers.LONG_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.IntFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseXorIntFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "^(II)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitXorIntFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitXorIntFunction extends IntFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitXorIntFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public int getInt(Record rec) {
final int l = left.getInt(rec);
final int r = right.getInt(rec);
return l != Numbers.INT_NaN && r != Numbers.INT_NaN ? l ^ r : Numbers.INT_NaN;
}
}
}
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin.engine.functions.math;
import io.questdb.cairo.CairoConfiguration;
import io.questdb.cairo.sql.Function;
import io.questdb.cairo.sql.Record;
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.SqlException;
import io.questdb.griffin.SqlExecutionContext;
import io.questdb.griffin.engine.functions.BinaryFunction;
import io.questdb.griffin.engine.functions.LongFunction;
import io.questdb.std.Numbers;
import io.questdb.std.ObjList;
public class BitwiseXorLongFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "^(LL)";
}
@Override
public Function newInstance(ObjList<Function> args, int position, CairoConfiguration configuration, SqlExecutionContext sqlExecutionContext) throws SqlException {
return new BitXorLongFunction(position, args.getQuick(0), args.getQuick(1));
}
public static final class BitXorLongFunction extends LongFunction implements BinaryFunction {
private final Function left;
private final Function right;
public BitXorLongFunction(int position, Function left, Function right) {
super(position);
this.left = left;
this.right = right;
}
@Override
public Function getLeft() {
return left;
}
@Override
public Function getRight() {
return right;
}
@Override
public long getLong(Record rec) {
final long l = left.getLong(rec);
final long r = right.getLong(rec);
return l != Numbers.LONG_NaN && r != Numbers.LONG_NaN ? l ^ r : Numbers.LONG_NaN;
}
}
}
......@@ -36,7 +36,7 @@ import io.questdb.std.ObjList;
public class PowDoubleFunctionFactory implements FunctionFactory {
@Override
public String getSignature() {
return "^(DD)";
return "power(DD)";
}
@Override
......
......@@ -23,6 +23,7 @@
******************************************************************************/
import io.questdb.griffin.FunctionFactory;
import io.questdb.griffin.engine.functions.math.*;
open module io.questdb {
requires transitive jdk.unsupported;
......@@ -530,6 +531,16 @@ open module io.questdb {
io.questdb.griffin.engine.functions.analytic.RowNumberFunctionFactory,
// metadata functions
io.questdb.griffin.engine.functions.metadata.BuildFunctionFactory
io.questdb.griffin.engine.functions.metadata.BuildFunctionFactory,
// bit operations
BitwiseAndLongFunctionFactory,
BitwiseOrLongFunctionFactory,
BitwiseNotLongFunctionFactory,
BitwiseXorLongFunctionFactory,
BitwiseAndIntFunctionFactory,
BitwiseOrIntFunctionFactory,
BitwiseNotIntFunctionFactory,
BitwiseXorIntFunctionFactory
;
}
......@@ -492,3 +492,13 @@ io.questdb.griffin.engine.functions.analytic.RowNumberFunctionFactory
# metadata functions
io.questdb.griffin.engine.functions.metadata.BuildFunctionFactory
# Bitwise operators
io.questdb.griffin.engine.functions.math.BitwiseAndLongFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseOrLongFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseXorLongFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseNotLongFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseAndIntFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseOrIntFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseXorIntFunctionFactory
io.questdb.griffin.engine.functions.math.BitwiseNotIntFunctionFactory
\ No newline at end of file
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin;
import io.questdb.test.tools.TestUtils;
import org.junit.Test;
public class BitwiseTest extends AbstractGriffinTest {
@Test
public void testIntNot() throws Exception {
assertBitwiseOp("select ~1024", "-1025\n");
}
@Test
public void testIntNotNull() throws Exception {
assertBitwiseOp("select ~cast(NaN as int)", "NaN\n");
}
@Test
public void testIntOr() throws Exception {
assertBitwiseOp("select 2 | 4", "6\n");
}
@Test
public void testIntOrLeftNull() throws Exception {
assertBitwiseOp("select NaN | 4", "NaN\n");
}
@Test
public void testIntOrRightNull() throws Exception {
assertBitwiseOp("select 2 | NaN", "NaN\n");
}
@Test
public void testLongOr() throws Exception {
assertBitwiseOp("select 2L | 4", "6\n");
}
@Test
public void testLongOrLeftNull() throws Exception {
assertBitwiseOp("select NaN | 4L", "NaN\n");
}
@Test
public void testLongOrRightNull() throws Exception {
assertBitwiseOp("select 2L | NaN", "NaN\n");
}
@Test
public void testLongAnd() throws Exception {
assertBitwiseOp("select 6L & 4", "4\n");
}
@Test
public void testLongAndLeftNull() throws Exception {
assertBitwiseOp("select NaN & 4L", "NaN\n");
}
@Test
public void testLongAndRightNull() throws Exception {
assertBitwiseOp("select 2L & NaN", "NaN\n");
}
@Test
public void testIntAnd() throws Exception {
assertBitwiseOp("select 6 & 4", "4\n");
}
@Test
public void testIntAndLeftNull() throws Exception {
assertBitwiseOp("select NaN & 4", "NaN\n");
}
@Test
public void testIntAndRightNull() throws Exception {
assertBitwiseOp("select 2 & NaN", "NaN\n");
}
@Test
public void testIntXor() throws Exception {
assertBitwiseOp("select 6 ^ 4", "2\n");
}
@Test
public void testIntXorLeftNull() throws Exception {
assertBitwiseOp("select NaN ^ 4", "NaN\n");
}
@Test
public void testIntXorRightNull() throws Exception {
assertBitwiseOp("select 2 ^ NaN", "NaN\n");
}
@Test
public void testLongXor() throws Exception {
assertBitwiseOp("select 6L ^ 4", "2\n");
}
@Test
public void testLongXorLeftNull() throws Exception {
assertBitwiseOp("select NaN ^ 4L", "NaN\n");
}
@Test
public void testLongXorRightNull() throws Exception {
assertBitwiseOp("select 2L ^ NaN", "NaN\n");
}
@Test
public void testLongNot() throws Exception {
assertBitwiseOp("select ~255L", "-256\n");
}
@Test
public void testLongNotNull() throws Exception {
assertBitwiseOp("select ~cast(NaN as long)", "NaN\n");
}
private void assertBitwiseOp(String sql, String expected) throws Exception {
assertMemoryLeak(() -> TestUtils.assertSql(
compiler,
sqlExecutionContext,
sql,
sink,
"column\n" +
expected
));
}
}
......@@ -508,7 +508,7 @@ public class ExpressionParserTest extends AbstractCairoTest {
@Test
public void testComplexUnary2() throws Exception {
x("ab^-", "-a^b");
x("a-b^", "-a^b");
}
@Test
......
/*******************************************************************************
* ___ _ ____ ____
* / _ \ _ _ ___ ___| |_| _ \| __ )
* | | | | | | |/ _ \/ __| __| | | | _ \
* | |_| | |_| | __/\__ \ |_| |_| | |_) |
* \__\_\\__,_|\___||___/\__|____/|____/
*
* Copyright (c) 2014-2019 Appsicle
* Copyright (c) 2019-2020 QuestDB
*
* Licensed 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 io.questdb.griffin;
import io.questdb.test.tools.TestUtils;
import org.junit.Test;
public class PowerTest extends AbstractGriffinTest {
@Test
public void testPowerDouble() throws Exception {
assertMemoryLeak(() -> TestUtils.assertSql(
compiler,
sqlExecutionContext,
"select power(10.2, 3)",
sink,
"power\n" +
"1061.2080000000003\n"
));
}
@Test
public void testPowerDoubleLeftNull() throws Exception {
assertMemoryLeak(() -> TestUtils.assertSql(
compiler,
sqlExecutionContext,
"select power(NaN, 3)",
sink,
"power\n" +
"NaN\n"
));
}
@Test
public void testPowerDoubleRightNull() throws Exception {
assertMemoryLeak(() -> TestUtils.assertSql(
compiler,
sqlExecutionContext,
"select power(1.5, NaN)",
sink,
"power\n" +
"NaN\n"
));
}
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册