Sqlserver
 sql >> Baza danych >  >> RDS >> Sqlserver

AKTUALIZUJ, jeśli istnieje, wstawiaj w SQL Server 2008

Wiele osób zasugeruje użycie MERGE , ale ostrzegam przed tym. Domyślnie nie chroni Cię przed współbieżnością i warunkami wyścigu bardziej niż wieloma oświadczeniami, ale wprowadza inne zagrożenia:

  • Zachowaj ostrożność z instrukcją MERGE SQL Server
  • Czego unikać, jeśli chcesz korzystać z funkcji MERGE
  • Wzorce i antywzorce SQL Server UPSERT

Nawet przy dostępnej „prostszej” składni nadal wolę to podejście (obsługa błędów pominięta dla zwięzłości):

SET TRANSACTION ISOLATION LEVEL SERIALIZABLE;
BEGIN TRANSACTION;
UPDATE dbo.table SET ... WHERE PK = @PK;
IF @@ROWCOUNT = 0
BEGIN
  INSERT dbo.table(PK, ...) SELECT @PK, ...;
END
COMMIT TRANSACTION;

Więcej informacji na temat tego UPSERT podejście tutaj:

  • Proszę przestać używać tego antywzorca UPSERT

Wiele osób zasugeruje w ten sposób:

SET TRANSACTION ISOLATION LEVEL SERIALIZABLE;
BEGIN TRANSACTION;
IF EXISTS (SELECT 1 FROM dbo.table WHERE PK = @PK)
BEGIN
  UPDATE ...
END
ELSE
BEGIN
  INSERT ...
END
COMMIT TRANSACTION;

Ale wszystko to zapewnia, że ​​może być konieczne dwukrotne przeczytanie tabeli, aby zlokalizować wiersze, które mają zostać zaktualizowane. W pierwszym przykładzie wystarczy raz zlokalizować wiersze. (W obu przypadkach, jeśli nie zostaną znalezione żadne wiersze z początkowego odczytu, nastąpi wstawienie).

Inni zasugerują w ten sposób:

BEGIN TRY
  INSERT ...
END TRY
BEGIN CATCH
  IF ERROR_NUMBER() = 2627
    UPDATE ...
END CATCH

Jest to jednak problematyczne, jeśli nie z innego powodu niż umożliwienie SQL Serverowi przechwytywania wyjątków, którym można było zapobiec w pierwszej kolejności, jest znacznie droższe, z wyjątkiem rzadkiego scenariusza, w którym prawie każde wstawienie kończy się niepowodzeniem. Udowadniam to tutaj:

  • Sprawdzanie potencjalnych naruszeń ograniczeń przed wejściem TRY/CATCH
  • Wpływ na wydajność różnych technik obsługi błędów

Nie jesteś pewien, co Twoim zdaniem zyskasz dzięki pojedynczemu oświadczeniu; Myślę, że nic nie zyskasz. MERGE jest pojedynczą instrukcją, ale i tak naprawdę musi wykonać wiele operacji - nawet jeśli sprawia, że ​​myślisz, że tak nie jest.




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Podłączanie Delphi w systemie Linux do SQL Server

  2. Wyjaśnienie SQL Server (localdb)\v11.0

  3. Przywracanie głównej bazy danych programu SQL Server

  4. Równoległe przywracanie kopii zapasowej serwera SQL Server -2

  5. Lista formatów dat dostępnych z CONVERT() w SQL Server