DIVIDE_BY_ZERO 错误类

SQLSTATE: 22012

被零除。 使用 try_divide 容许除数为 0,并返回 NULL。 如有必要,请将 <config> 设置为“false”以绕过此错误。

参数

  • ansiConfig:要更改行为的配置的名称。

说明

每当 Azure Databricks 尝试将 INTERVAL 或数字除以 0 时,都会引发此错误。 与此错误一起提供的上下文信息隔离了发生错误的对象和表达式。 可能导致此错误的函数和运算符(例如 mod)包括那些在更复杂的公式中执行除法的函数和运算符。

缓解措施

错误的缓解方法取决于具体原因:

  • 导致错误的表达式是否正确?

    如果表达式不正确,则纠正表达式,让 0 值不再出现,然后重试查询。

  • 数据是否正确?

    如果输入数据应该能够导致 0 传递值,则可能需要修复源中的数据,或在将数据作为参数传递给函数之前清理数据。

    数据清理可能表明需要排除有问题的行,使用 nullif(expr, 0)0 值转换为 NULL,或者使用 if(expr = 0, alt, expr) 将数据转换为另一个可接受的值。

如果表达式和数据正确,并且想要容忍除以零,则可以使用 try_divide。 作为替代方法,请将参数更改为 nullif(expr, 0)。 这将导致表达式返回 NULL 而不是错误。 如果希望使用 nvl(try_divide(expr1, expr2), alt) 将生成的 NULL 转换为替代值,如加法 0 或乘法 1 的中性元素。

作为最后手段的解决方案,当无法更改表达式或数据流时,可以通过将提供的 ansiconfig 项设置为 false 来禁用此 ANSI 行为。 请注意,此设置是超出直接错误条件的后续设置

示例

-- A DIVIDE_BY_ZERO in a embedded in view. The context information isolates the faiing function.
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1/val FROM VALUES(1), (0) AS T(val);
> SELECT c1 FROM v;
  [DIVIDE_BY_ZERO] Division by zero. To return NULL instead, use `try_divide`. If necessary set "spark.sql.ansi.enabled" to false (except for ANSI interval type) to bypass this error.
  == SQL of VIEW v(line 1, position 7) ==
  SELECT 1/val FROM VALUES(1), (0) AS T(val)
         ^^^^^

-- Tolerating division by zero by turning the result to NULL using try_divide.
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT try_divide(1, val) FROM VALUES(1), (0) AS T(val);
> SELECT c1 FROM v;
  1
  NULL

-- Tolerating division by zero by turning the result to NULL using nullif
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1 / nullif(val, 0) FROM VALUES(1), (0) AS T(val);
> SELECT c1 FROM v;
  1
  NULL

-- Filtering out offensive rows
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1/val FROM VALUES(1), (0) AS T(val) WHERE val != 0;
> SELECT c1 FROM v;
  1

-- Turning division by zero into division by a small number.
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1 / if(val = 0, 1e-10, val) FROM VALUES(1), (0) AS T(val);
> SELECT c1 FROM v;
  1
  10000000000

-- Turning division by zero into a neutral element for addition.
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT nvl(try_divide(1, val), 0) FROM VALUES(1), (0) AS T(val);
> SELECT c1 FROM v;
  1
  0

-- Disabling ANSI mode in Databricks SQL for the view definition only.
> SET ANSI_MODE = false;
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1/val FROM VALUES(1), (0) AS T(val);
> SET ANSI_MODE = true;

> SELECT c1 FROM v;
  1
  NULL

-- Disabling ANSI mode in Databricks Runtime for the view definition only.
> SET spark.sql.ansi.enabled = false;
> CREATE OR REPLACE TEMPORARY VIEW v(c1) AS SELECT 1/val FROM VALUES(1), (0) AS T(val);
> SET spark.sql.ansi.enabled = true;

> SELECT c1 FROM v;
  1
  NULL