Более простой способ НЕ ОТЛИЧАЕТСЯ ОТ

Является ли следующий самый простой способ написать IS NOT DISTINCT FROM без использования этого предложения?

   ColA IS NULL AND ColB IS NOT NULL 
OR ColA IS NOT NULL AND ColB IS NULL
OR ColA != ColB

Или есть более простой способ?

Вам, безусловно, понадобятся скобки вокруг разделов и , если вы хотите, чтобы это работало.

Dale K 04.06.2023 05:40

Почему образцы данных могут помочь? Все, что для этого требуется, это знание того, что НЕ ОТЛИЧАЕТСЯ ОТ

Martin Smith 04.06.2023 11:59
ReactJs | Supabase | Добавление данных в базу данных
ReactJs | Supabase | Добавление данных в базу данных
Это и есть ваш редактор таблиц в supabase.👇
Понимание Python и переход к SQL
Понимание Python и переход к SQL
Перед нами лабораторная работа по BloodOath:
5
2
131
3
Перейти к ответу Данный вопрос помечен как решенный

Ответы 3

Более простой способ — использовать NOT из метода Equals, чтобы написать его. Например:

WITH tbl(colA, colB) AS (
    SELECT 1,2 UNION ALL
    SELECT NULL,1 UNION ALL
    SELECT 1,NULL UNION ALL
    SELECT NULL,NULL
) 
SELECT 
    colA, 
    colB,
    colA=colB OR (colA IS NULL AND colB IS NULL) eq,
    NOT( colA=colB OR (colA IS NULL AND colB IS NULL) ) neq
FROM
    tbl

Это не сработает, из-за того, как СУБД обрабатывают значения NULL и равенства. Ни один ваш исходный код, доступный в посте, не заменит IS DISTINCT FROM.
lemon 04.06.2023 03:34

@lemon извините, я не понимаю, не могли бы вы уточнить? У меня это работает: gyazo.com/34b16e330696c1d7f7db2c4f661578b9.

David542 04.06.2023 03:54

Разве cola<>colb и Not (cola<>colb) недостаточно для значения отличной от этой причины, поскольку NULLS возвращает разные значения для разных столбцов или строк

Himanshu 04.06.2023 04:47

Конструктор таблиц values более лаконичен, чем union all

Dale K 04.06.2023 06:03

Вам необходимо рассмотреть все возможные крайние случаи для вашего варианта использования, которые я включил по предоставленной ссылке в моем первом комментарии.

lemon 04.06.2023 10:39

Когда вам удается использовать условия, которые дают вам вывод IS DISTINCT FROM во всех возможных крайних случаях, и отрицание вашего полного набора условий дает вам точный результат IS NOT DISTINCT FROM, тогда вы можете сказать, что нашли набор условий, которые могут заменить это оператор.

lemon 04.06.2023 10:52

Я не понял, что вы спрашиваете здесь, на примере. Но вот более простая версия вашего запроса

Select *, case when distinct_from_v1 = 1 then 0 else 1 end as not_distinct_from_v1
  from 
   (SELECT colA, colB, 
           CASE WHEN colA IS DISTINCT FROM colB THEN 1 ELSE 0 END AS distinct_from,
           case when Cola + colb is not null 
                then 
                case when cola=colb then 0 
                     else 1 
                end
           else
                case when concat(cola,colb) in (cola,colb)  then 1 else 0 end
      end  as distinct_from_v1
    FROM tab) t;

Рабочая рабочий пример https://dbfiddle.uk/aVKsWNvz

Он работает почти во всех базах данных || поддерживается и в Sql Server.

Himanshu 04.06.2023 07:30
Это тоже не работает, потому что ни один из двух ваших сгенерированных столбцов не равен столбцу IS (NOT) DISTINCT FROM.
lemon 04.06.2023 10:49

@lemon работает нормально, я представил 0 как ложь, а 1 как истину. только в случаях обоих нулей это разные

Himanshu 04.06.2023 17:57

Одного невыполненного условия достаточно, чтобы он сам по себе был другим оператором. Два оператора эквивалентны только тогда, когда они ведут себя одинаково при любых условиях.

lemon 04.06.2023 18:01

@lemon проверь сейчас

Himanshu 04.06.2023 18:28
Пока нет: отрицание обоих операторов также должно привести к прямо противоположному результату. В вашем случае вы получаете последние три записи с 1 и первые две с 0. Это чрезвычайно сложная задача, безошибочно.
lemon 04.06.2023 18:35

Вы можете сохранить значение во вложенном запросе и выполнить NOT во внешнем запросе.

Himanshu 04.06.2023 19:06

Еще раз отредактировал, проверьте.

Himanshu 04.06.2023 19:11
Ответ принят как подходящий

IS [NOT] DISTINCT FROM — самый простой способ сделать это.

В предыдущих версиях можно было сделать (Fiddle)

  • EXISTS (SELECT colA INTERSECT SELECT colB) за IS NOT DISTINCT
  • EXISTS (SELECT colA EXCEPT SELECT colB) за IS DISTINCT

хотя более подробно

  • NOT EXISTS (SELECT colA INTERSECT SELECT colB)

иногда дает лучший план выполнения для случая IS DISTINCT (пример).

См. Недокументированные планы запросов: сравнение равенства для обсуждения различных альтернативных подходов к этому.

Как правило, я обнаружил, что планы выполнения подходят для описанных выше подходов, хотя иногда я обнаруживал, что записываю условие полностью как

  • WHERE ColA = ColB OR (ColA IS NULL AND ColB IS NULL) (для случая NOT DISTINCT)
  • WHERE ColA <> ColB OR (ColA IS NULL AND ColB IS NOT NULL) OR (ColA IS NOT NULL AND ColB IS NULL) (для случая DISTINCT)

дает лучший план выполнения.

INTERSECT/EXCEPT очень удобны, когда вам нужно сделать этот тип сравнения по нескольким столбцам...

EXISTS (SELECT t1.colA, t1.colB, t1.colC 
        INTERSECT 
        SELECT t2.colA, t2.colB, t2.colC)

... но проверьте планы, чтобы убедиться, что они эффективно оптимизируются в том контексте, в котором вы их используете.

спасибо за этот ответ, это, конечно, правильно. Не уверен, почему так много людей проголосовали против / закрыли вопрос, возможно, люди не знают, что означает IS DISTINCT FROM.

David542 06.06.2023 04:47

Другие вопросы по теме