Geriausias būdas gauti įvestos eilutės tapatybę?

Koks yra geriausias būdas įterpti įterptos eilutės IDENTUMĄ?

Žinau apie @@IDENTITY ir IDENT_CURRENT ir SCOPE_IDENTITY , bet nesuprantu su kiekvienu susijusiu privalumu ir trūkumais.

Ar kas nors paaiškins skirtumus ir kada juos naudosiu?

875
04 сент. nustatė Odedas rugsėjo 04 d. 2008-09-04 00:32 '08 ne 0:32 2008-09-04 00:32
@ 11 atsakymų
1154
04 сент. Atsakymą pateikia bdukes 04 sep . 2008-09-04 00:38 '08 ne 0:38 2008-09-04 00:38

Manau, kad saugiausias ir tiksliausias būdas įterpti įvestą ID naudos išvados sąlygą.

pavyzdžiui (paimtas iš šio MSDN straipsnio)

border=0
 USE AdventureWorks2008R2; GO DECLARE @MyTableVar table( NewScrapReasonID smallint, Name varchar(50), ModifiedDate datetime); INSERT Production.ScrapReason OUTPUT INSERTED.ScrapReasonID, INSERTED.Name, INSERTED.ModifiedDate INTO @MyTableVar VALUES (N'Operator error', GETDATE()); --Display the result set of the table variable. SELECT NewScrapReasonID, Name, ModifiedDate FROM @MyTableVar; --Display the result set of the table. SELECT ScrapReasonID, Name, ModifiedDate FROM Production.ScrapReason; GO 
149
20 мая '11 в 17:43 2011-05-20 17:43 atsakymą pateikė „ Orry “ gegužės 20 d. 11 d. 17:43 2011-05-20 17:43

Aš sakau tą patį kaip ir kiti vaikinai, todėl viskas gerai, aš tiesiog bandau padaryti jį suprantamesnę.

@@IDENTITY grąžina paskutinio elemento ID, kurį kliento ryšys įdėjo į duomenų bazę.
Daugeliu atvejų tai veikia gerai, bet kartais įsijungia ir įterpia naują eilutę, apie kurią nežinote, ir jūs gaunate iš šios naujos eilutės identifikatorių, o ne tą, kurią norite

SCOPE_IDENTITY() išsprendžia šią problemą. Ji grąžina paskutinio dalyko, kurį įdėjote į duomenų bazę, SQL kodą. Jei paleidžiami ir sukuriami papildomi stygos, jie nepateiks neteisingos vertės. Hooray

IDENT_CURRENT grąžina paskutinį asmens IDENT_CURRENT identifikatorių. Jei bet kuri kita programa atsitiktinai patenka į kitą eilutę ne darbo valandomis, gausite šios eilutės identifikatorių, o ne jūsų.

Jei norite saugiai žaisti, visada naudokite SCOPE_IDENTITY() . Jei laikysitės @@IDENTITY , ir kas nors nusprendžia vėliau pridėti trigerį, visas jūsų kodas bus pertrauktas.

90
04 сент. atsakymą pateikė „ Orion Edwards“ rugsėjo 04 d 2008-09-04 00:44 '08 0:44 2008-09-04 00:44

Geriausias (aiškiausias: saugiausias) būdas gauti naujai įterptos linijos tapatybę yra naudoti output sąlygą:

 create table TableWithIdentity ( IdentityColumnName int identity(1, 1) not null primary key, ... ) -- type of this table column must match the type of the -- identity column of the table you'll be inserting into declare @IdentityOutput table ( ID int ) insert TableWithIdentity ( ... ) output inserted.IdentityColumnName into @IdentityOutput values ( ... ) select @IdentityValue = (select ID from @IdentityOutput) 
51
29 апр. Atsakymas, kurį pateikė Ian Kemp Apr 29 2013-04-29 10:22 '13, 10:22, 2013-04-29 10:22

Pridėti

 SELECT CAST(scope_identity() AS int); 

tada iki jūsų įterptųjų SQL pareiškimo pabaigos

 NewId = command.ExecuteScalar() 

gausite jį.

19
30 марта '15 в 21:25 2015-03-30 21:25 atsakymą pateikė Jim kovo 15 d. 15:25 2015-03-30 21:25

MSDN

@@ IDENTITY, SCOPE_IDENTITY ir IDENT_CURRENT yra panašios funkcijos, nes grąžina paskutinę vertę, įtrauktą į lentelės IDENTITY stulpelį.

@@ IDENTITY ir SCOPE_IDENTITY grąžins paskutinę identifikavimo vertę, sukurtą bet kurioje dabartinės sesijos lentelėje. Tačiau SCOPE_IDENTITY grąžina vertę tik pagal dabartinę taikymo sritį; @@ IDENTITY neapsiriboja konkrečia sritimi.

IDENT_CURRENT neapsiriboja taikymo sritimi ir sesija; ji apsiriboja nurodytoje lentelėje. IDENT_CURRENT grąžina konkrečiai lentelei sukurtą identifikatoriaus vertę bet kurioje sesijoje ir bet kurioje srityje. Daugiau informacijos žr. IDENT_CURRENT.

12
04 сент. Atsakymą davė Jakub Šturc . 2008-09-04 00:37 '08 2008-09-04 00:37 00:37

@@ IDENTITY yra paskutinis identifikavimas, įterptas naudojant dabartinį SQL ryšį. Tai gera vertė, jei norite grįžti iš įrašytos įterptos procedūros, kur tiesiog reikia identifikavimo, įrašyto jūsų naujam įrašui, ir nesvarbu, ar po to pridedama daugiau eilučių.

SCOPE_IDENTITY yra paskutinis identifikavimas, įterptas naudojant dabartinį SQL ryšį, ir dabartinėje taikymo srityje - tai yra, jei antrasis įterpimas buvo įdėtas remiantis trigeriu po įterpimo - jis bus rodomas SCOPE_IDENTITY, tik atliktas įterpimas. Sąžiningai, aš niekada neturėjau priežasties jį naudoti.

IDENT_CURRENT (table_name) yra paskutinis identifikavimas, įterptas nepriklausomai nuo ryšio ar apimties. Tai galite naudoti, jei norite gauti dabartinę IDENTITY reikšmę lentelėje, kurioje neįrašėte įrašo.

11
04 сент. Atsakymas, kurį pateikė Guy Starbuck 04 Sep. 2008-09-04 00:42 '08 0:42 2008-09-04 00:42

Kai naudojate „Entity Framework“, ji viduje naudoja OUTPUT metodą, kad grąžintų naujai įterptą identifikatoriaus vertę.

 DECLARE @generated_keys table([Id] uniqueidentifier) INSERT INTO TurboEncabulators(StatorSlots) OUTPUT inserted.TurboEncabulatorID INTO @generated_keys VALUES('Malleable logarithmic casing'); SELECT t.[TurboEncabulatorID ] FROM @generated_keys AS g JOIN dbo.TurboEncabulators AS t ON g.Id = t.TurboEncabulatorID WHERE @@ROWCOUNT > 0 

Išvesties rezultatai saugomi laikinajame lentelės kintamajame, prijungtame atgal prie stalo, ir grąžina eilutės vertę iš lentelės.

Pastaba Aš nesuprantu, kodėl EF viduje prisijungs prie efemerinės lentelės atgal į tikrąjį stalą (kokiomis aplinkybėmis jie nesutampa).

Tačiau tai daroma EF.

Šis metodas ( OUTPUT ) galimas tik „SQL Server 2008“ arba naujesnėje versijoje.

10
04 нояб. Atsakymą pateikė Ian Boyd 04 lapkričio. 2016-11-04 18:05 '16 at 18:05 pm 2016-11-04 18:05

Visada naudokite „display_identity“ (), NIEKADA nereikia nieko.

8
09 окт. atsakymas erikkallen 09 Oct 2009-10-09 23:35 '09, 11:35 AM 2009-10-09 23:35

Aš negaliu kalbėti su kitomis SQL Server versijomis, tačiau 2012 m. Produkcija tiesiogiai veikia tik gerai. Jums nereikia nerimauti dėl laikinojo stalo.

 INSERT INTO MyTable OUTPUT INSERTED.ID VALUES (...) 

Beje, šis metodas veikia ir įterpiant kelias eilutes.

 INSERT INTO MyTable OUTPUT INSERTED.ID VALUES (...), (...), (...) 

Išeiti

 ID 2 3 4 
1
06 июня '18 в 19:58 2018-06-06 19:58 MarredCheese atsakymą pateikė birželio 06 d. 18 val. 18:58. 2018-06-06 19:58

Po įterpimo pareiškimo turite jį pridėti. Ir patikrinkite lentelės, kurioje yra duomenys, pavadinimą. Jūs gausite dabartinę eilutę, kurioje eilutė paveikė tik dabar įterpti pareiškimą.

 IDENT_CURRENT('tableName') 
0
31 дек. Atsakymą pateikė Khan Ataur Rahman gruodžio 31 d. 2017-12-31 09:04 '17 at 9:04 2017-12-31 09:04

Kiti klausimai apie arba Užduoti klausimą