T-SQL Можно ли выполнить обновление / вставку с помощью одной быстрой операции - PullRequest
6 голосов
/ 24 ноября 2011

Допустим, у меня есть таблица, и я хочу вставить строку. Ключ новой строки может уже соответствовать ключу существующей строки в таблице, и в этом случае я хочу обновить существующую строку. Или он может не существовать в таблице, и в этом случае должна быть вставлена ​​новая строка.

Какой самый эффективный способ выполнить такую ​​операцию? Я думал о том, чтобы сначала сделать SELECT (возможно, с EXISTS), чтобы увидеть, присутствует ли конкретный ключ, затем UPDATE, если присутствует, и INSERT, если нет. Вы, вероятно, должны были бы сохранить UPDLOCK и HOLDLOCK для этой комбинации утверждений, чтобы также избежать условий гонки. Это кажется слишком сложным и неэффективным.

Мне было интересно, есть ли более эффективный способ сделать это в SQL Server 2008R2.

1 Ответ

10 голосов
/ 24 ноября 2011

SQL Server 2008 и новее имеют оператор MERGE, который именно это и делает.

Подробнее см. В MSDN Books Online документах по MERGE .

По сути, вам нужночетыре вещи:

  • a source (таблица или представление или встроенный оператор SELECT)
  • a target
  • a JOIN условие, связывающее два оператора
  • для случаев, когда есть MATCH (строки существуют как в источнике, так и в цели), NOT MATCHED (когда строка еще не существует в цели) ии так далее

Таким образом, вы в основном определяете что-то вроде:

MERGE (targettable) AS t
USING (sourcetable) AS s
ON (JOIN condition between s and t)
WHEN MATCHED THEN
   UPDATE SET t.Col1 = s.Col1, t.Col2 = s.Col2 (etc.)
WHEN NOT MATCHED THEN
   INSERT(Col1, Col2, ..., ColN) VALUES(s.Col1, s.Col2, ......, s.ColN)

Это делается как одно утверждение и высоко оптимизируется SQL Server.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...