это можно записать с помощью внешнего соединения - PullRequest
0 голосов
/ 08 декабря 2009

Требуется скопировать строки из таблицы B в таблицу A. Необходимо скопировать только строки с идентификатором, который еще не существует:

INSERT INTO A(id, x, y)
SELECT id, x, y
FROM B b
WHERE b.id IS NOT IN (SELECT id FROM A WHERE x='t');
                                       ^^^^^^^^^^^

Теперь я пытался написать это с помощью внешнего соединения, чтобы сравнить пути объяснения, но я не могу написать это (по крайней мере, эффективно).

Обратите внимание, что sql, выделенный ^, делает это хитрым.

Ответы [ 4 ]

4 голосов
/ 08 декабря 2009

1001 * попробовать *

INSERT INTO A(id, x, y)
SELECT id, x, y
FROM TableB b
  Left Join TableA a
     On a.Id = b.Id
        And a.x = 't'
Where a.Id Is Null

Но я предпочитаю представление подзапроса, так как думаю, что оно более четко выражает то, что вы делаете.

3 голосов
/ 08 декабря 2009

Почему ты не доволен тем, что имеешь? Если вы проверите свой план объяснения, я обещаю, что в нем говорится, что анти-объединение выполняется, если оптимизатор считает, что это наиболее эффективный способ (что, скорее всего, будет).

Для всех, кто читает это: SQL не то, что на самом деле выполняется. SQL - это способ сообщить базе данных, что вы хотите, а не что делать. Все достойные базы данных смогут обрабатывать NOT EXISTS и NOT IN как равные (когда они равны, то есть отсутствуют нулевые значения) и выполнять анти-объединение. Трюк с внешним соединением и условием IS NULL не работает на SQL Server, хотя (SQL Server недостаточно умен, чтобы преобразовать его в соединение).

0 голосов
/ 04 ноября 2011
INSERT INTO A (id, x, y)
SELECT
    B.id, B.x, B.y
FROM
    B
WHERE
    NOT EXISTS (SELECT * FROM A WHERE B.id = A.id AND A.x = 't')
0 голосов
/ 08 декабря 2009

Ваш запрос будет работать лучше, чем запрос с внешним объединением.

Полагаю, следующий запрос выполнит эту работу:

INSERT INTO A(id, x, y)
SELECT id, x, y
FROM B b
LEFT JOIN A a
ON b.id = a.id AND NOT a.x='t'
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...