SQL Server 2005 Implementace MySQL REPLACE INTO?

hlasů
73

MySQL má tento neuvěřitelně užitečný přesto properitary REPLACE INTOSQL příkaz.

Lze to snadno emulován v SQL Server 2005?

Spuštění nové transakce, dělá Select()a pak buď UPDATEnebo INSERT IGNORE a COMMITje vždy trochu bolesti, zvláště když to dělá v žádosti, a proto vždy udržet 2 verze prohlášení.

Zajímalo by mě, jestli existuje jednoduchý a univerzální způsob, jak implementovat tuto funkci do SQL Server 2005?

Položena 01/08/2008 v 23:13
zdroj uživatelem
V jiných jazycích...                            


4 odpovědí

hlasů
53

To je něco, co mě štve o MSSQL ( chvástat se na mém blogu ). Přeji MSSQL podporován upsert.

@ Dillie-O Kód je dobrý způsob, jak ve starších verzích SQL (1 hlasování), ale stále je v podstatě dvě operace IO (dále jen existsa pak update, nebo insert)

Je tu něco lepší způsob, jak na tento post , v podstatě:

--try an update
update tablename 
set field1 = 'new value',
    field2 = 'different value',
    ...
where idfield = 7

--insert if failed
if @@rowcount = 0 and @@error = 0
    insert into tablename 
           ( idfield, field1, field2, ... )
    values ( 7, 'value one', 'another value', ... )

To snižuje ji do jedné operace IO, pokud je to aktualizovat nebo dva, pokud vložka.

MS SQL2008 zavádí mergeod SQL: 2003 standardu:

merge tablename as target
using (values ('new value', 'different value'))
    as source (field1, field2)
    on target.idfield = 7
when matched then
    update
    set field1 = source.field1,
        field2 = source.field2,
        ...
when not matched then
    insert ( idfield, field1, field2, ... )
    values ( 7,  source.field1, source.field2, ... )

Teď je to opravdu jen jedna operace IO, ale strašné číslo :-(

Odpovězeno 15/08/2008 v 13:50
zdroj uživatelem

hlasů
20

Funkčnost hledáte se tradičně nazývá UPSERT. Aspoň vědět, jak se jmenuje vám mohou pomoci najít to, co hledáte.

Nemyslím si, že SQL Server 2005 má nějaké skvělé způsoby, jak to udělat. 2008 zavádí výraz SLOUČENÍ, které lze použít k dosažení tohoto cíle, jak je uvedeno v: http://www.databasejournal.com/features/mssql/article.php/3739131 nebo http://blogs.conchango.com/davidportas/archive/ 2007/11 / 14 / SQL Server-2008-MERGE.aspx

Sloučení bylo k dispozici v beta verzi z roku 2005, ale odstranit ji v konečné verzi.

Odpovězeno 01/08/2008 v 23:22
zdroj uživatelem

hlasů
15

Co se upsert / merge dělá, je něco v tom smyslu, ze ...

IF EXISTS (SELECT * FROM [Table] WHERE Id = X)
   UPDATE [Table] SET...
ELSE
   INSERT IGNORE  INTO [Table]

Takže doufejme, že kombinace těchto článků a tento pseudo kód může dostat věci do pohybu.

Odpovězeno 01/08/2008 v 23:31
zdroj uživatelem

hlasů
9

Napsal jsem blog post o tomto problému .

Pointa je, že pokud chcete levné aktualizace ... a chcete být bezpečné pro souběžné používání. Snaž se:

update t
set hitCount = hitCount + 1
where pk = @id

if @@rowcount < 1 
begin 
   begin tran
      update t with (serializable)
      set hitCount = hitCount + 1
      where pk = @id
      if @@rowcount = 0
      begin
         insert t (pk, hitCount)
         values (@id,1)
      end
   commit tran
end

Tímto způsobem budete mít 1 operaci pro aktualizace a max 3 operací pro vložkami. Takže, pokud jste se obvykle aktualizuje se jedná o bezpečný levné řešení.

Byl bych velmi opatrný, aby použít cokoliv, která je nebezpečná pro souběžné používání. Je to opravdu snadné získat primární klíč porušení nebo duplicitní řádky ve výrobě.

Odpovězeno 21/09/2008 v 23:05
zdroj uživatelem

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more