Udostępnij za pośrednictwem


DIVIDE_BY_ZERO klasa błędu

SQLSTATE: 22012

Dzielenie według zera. Użyj try_divide, aby tolerować sytuację, gdy dzielnik jest 0, i zamiast tego zwracać wartość NULL. W razie potrzeby ustaw <config> na wartość "false", aby pominąć ten błąd.

Parametry

  • ansiConfig: nazwa konfiguracji, aby zmienić zachowanie.

Wyjaśnienie

Usługa Azure Databricks zgłasza ten błąd za każdym razem, gdy próbuje podzielić INTERWAŁ lub liczbę przez 0. Informacje kontekstowe dostarczone z tym błędem izoluje obiekt i wyrażenie, w którym wystąpił błąd. Funkcje i operatory, takie jak mod, które mogą powodować ten błąd, obejmują te, które wykonują dzielenie w ramach bardziej złożonych formuł.

Łagodzenia

Ograniczenie ryzyka błędu zależy od przyczyny:

  • Czy wyrażenie powoduje błąd?

    Jeśli wyrażenie jest niepoprawne, popraw je, aby wartość 0 nie mogła wystąpić, i spróbuj ponownie wykonać zapytanie.

  • Czy dane są poprawne?

    Jeśli dane wejściowe powinny być w stanie spowodować przekazanie wartości 0, może być konieczne naprawienie danych w źródle lub wyczyszczenie ich przed przekazaniem danych do funkcji jako argumentu.

    Czyszczenie danych może oznaczać wykluczenie obraźliwych wierszy w celu przekonwertowania wartości 0 na NULL przy użyciu nullif(expr, 0)lub przekonwertowania danych na inną akceptowalną wartość przy użyciu if(expr = 0, alt, expr).

Jeśli wyrażenie i dane są poprawne i chcesz tolerować dzielenie według zera, możesz użyć try_divide. Alternatywnie zmień argument na nullif(expr, 0). To spowoduje, że wynik wyrażenia będzie NULL zamiast błędu. Jeśli wolisz, możesz nvl(try_divide(expr1, expr2), alt) przekształcić wynikowe NULL w wartości alternatywne, takie jak elementy neutralne dla dodawania 0 lub mnożenia 1.

Jako rozwiązanie ostateczne, gdy wyrażenie lub przepływ danych nie mogą zostać zmienione, możesz wyłączyć to zachowanie ANSI, ustawiając podaną ansiconfig na wartość false. Należy pamiętać, że to ustawienie jest wynikowe poza natychmiastowym warunkiem błędu.

Przykłady

-- 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