[ 
https://issues.apache.org/jira/browse/CALCITE-3717?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17012532#comment-17012532
 ] 

Danny Chen commented on CALCITE-3717:
-------------------------------------

You are right, i re-produce this problem in JdbcTest with your demo sql, after 
some analysis of the generated code:

{code:java}
            public Object current() {
              final Object[] current = (Object[]) inputEnumerator.current();
              final int inp1_ = 
org.apache.calcite.runtime.SqlFunctions.toInt(current[1]);
              final int inp2_ = 
org.apache.calcite.runtime.SqlFunctions.toInt(current[2]);
              final int inp3_ = 
org.apache.calcite.runtime.SqlFunctions.toInt(current[3]);
              final java.math.BigDecimal v1 = new java.math.BigDecimal(
                inp1_ + inp2_ + inp3_);
              final java.math.BigDecimal v2 = 
$L4J$C$new_java_math_BigDecimal_1_0_;
              final int inp0_ = 
org.apache.calcite.runtime.SqlFunctions.toInt(current[0]);
              final java.math.BigDecimal v4 = new java.math.BigDecimal(
                inp0_);
              final java.math.BigDecimal v5 = 
org.apache.calcite.runtime.SqlFunctions.divide(v2, v4);
              final java.math.BigDecimal v7 = new java.math.BigDecimal(
                inp2_ + inp3_);
              final java.math.BigDecimal v10 = new java.math.BigDecimal(
                inp1_);
              final java.math.BigDecimal v12 = 
org.apache.calcite.runtime.SqlFunctions.plus(v5, 
org.apache.calcite.runtime.SqlFunctions.divide(v2, v10));
              final java.math.BigDecimal v13 = new java.math.BigDecimal(
                inp3_);
              final java.math.BigDecimal v16 = new java.math.BigDecimal(
                inp2_);
              final java.math.BigDecimal v18 = 
org.apache.calcite.runtime.SqlFunctions.plus(v12, 
org.apache.calcite.runtime.SqlFunctions.divide(v2, v16));
              return inp0_ == 0 ? 
org.apache.calcite.runtime.SqlFunctions.multiply(v1, v2) : inp1_ == 0 ? 
org.apache.calcite.runtime.SqlFunctions.plus(v5, 
org.apache.calcite.runtime.SqlFunctions.multiply(v7, v2)) : inp2_ == 0 ? 
org.apache.calcite.runtime.SqlFunctions.plus(v12, 
org.apache.calcite.runtime.SqlFunctions.multiply(v13, v2)) : inp3_ == 0 ? v18 : 
org.apache.calcite.runtime.SqlFunctions.plus(v18, 
org.apache.calcite.runtime.SqlFunctions.divide(v2, v13));
            }

            static final java.math.BigDecimal 
$L4J$C$new_java_math_BigDecimal_1_0_ = new java.math.BigDecimal(
              "1.0");
          };
{code}


I believe that it is because Calcite generate the intermediate variable eagerly 
so that some the variables are "xx/0" which make the protection of the case 
when branch lost its functionality.

I'm not that familiar with the code generation, a solution to this is that 
instead of generate a variable, we should generate a method there, can you give 
some help [~donnyzone] ~


> Query fails with "division by zero" exception
> ---------------------------------------------
>
>                 Key: CALCITE-3717
>                 URL: https://issues.apache.org/jira/browse/CALCITE-3717
>             Project: Calcite
>          Issue Type: Bug
>            Reporter: Hank Miller
>            Priority: Major
>
> Hi, community. We use Calcite-1.21 to connect and compute data resident in 
> PostgreSQL and MySQL. It works pretty well. But we encountered a problem 
> yesterday.
> Firstly, we combine data from different datasources.
> Assume the combined table is _T(...., c1, c2, c3)_, in which _c1, c2, c3_ are 
> integer columns. Then according to our business logic, we need to perform 
> further data processing in Calcite.
> {code:java}
> select case when c1=0 then ..
>             when c2=0 then 1.0/c1 + ...
>             when c3=0 then 1.0/c1 + 1.0/c2 + ...
>        else -99.99 end 
> from T{code}
> However, the query throws "java.lang.ArithmeticException: Division by zero".
> Anything goes wrong?



--
This message was sent by Atlassian Jira
(v8.3.4#803005)

Reply via email to