In MS-SQL, come faccio a inserire in una tabella temporanea, e hanno un campo di identità creata, senza prima dichiarare la tabella temporanea?


36

Ho bisogno di selezionare una serie di dati in una tabella temporanea, per poi fare alcuni calcoli secondarie; Per aiutare a farlo funzionare in modo più efficiente, mi piacerebbe avere una colonna IDENTITY su quel tavolo. So che potrei dichiarare il tavolo prima con un'identità, quindi inserire il resto dei dati in esso, ma c'è un modo per farlo in 1 step?

+1

colonne IDENTITY rendere le cose coerenti per più utenti. PRIMARY KEY rende le cose efficienti. Usa entrambi per ottenere il massimo effetto. 23 set. 082008-09-23 20:28:18

64

Oh gente di poca fede:

SELECT *, IDENTITY(int) AS idcol 
    INTO #newtable 
    FROM oldtable 

http://msdn.microsoft.com/en-us/library/aa933208(SQL.80).aspx

  0

Non funziona se oldtable ha una colonna Identity 23 set. 082008-09-23 20:38:39

+1

Ma ovviamente, non puoi averne due. Basta non selezionare la colonna ident come parte della query 23 set. 082008-09-23 20:54:24

  0

Bisogna fare attenzione se si utilizza una clausola ORDER BY e si aspetta che "idcol" sia nello stesso ordine. http://support.microsoft.com/kb/273586 04 ott. 112011-10-04 18:28:36

  0

seleziona cast (CurrentID come int) come CurrentID che ti dovrebbe piacere se oldtable ha una colonna Identity 05 feb. 142014-02-05 17:58:29


-4

IIRC, il comando INSERT INTO utilizza lo schema della tabella di origine per creare la tabella temporanea. Questo fa parte del motivo per cui non puoi semplicemente provare a creare una tabella con una colonna aggiuntiva. Le colonne di identità sono internamente legate a un costrutto di SQL Server chiamato generatore.


-3

Si potrebbe fare un Select Into, che creerebbe la struttura della tabella al volo in base ai campi selezionati, ma non lo faccio pensa che creerà un campo di identità per te.


1

Per rendere le cose efficiente, è necessario fare dichiarare che una delle colonne da una chiave primaria:

ALTER TABLE #mytable 
ADD PRIMARY KEY(KeyColumn) 

che non avrà una variabile per il nome della colonna.

Fidati di me, sei MOLTO meglio fare una: CREATE #myTable TABLE (o eventualmente una DECLARE TABLE @myTable), che ti permette di impostare IDENTITY e PRIMARY KEY direttamente.

  0

Dipende; gli inserimenti in una tabella indicizzata sono (con poche eccezioni) più lenti di una tabella non indicizzata a causa della manutenzione della struttura B +; questa app potrebbe non avere dati sufficienti caricati nella tabella temporanea per rendere un indice utile. Dipende totalmente dalla situazione, e non abbiamo informazioni sufficienti per sapere 23 set. 082008-09-23 20:58:20

  0

Vuole una "identità" per "rendere le cose efficienti". Possiamo concludere che vorrebbe accedere agli oggetti con un ID che non esiste già. È facile da ordinare per un ID che non esiste già. 23 set. 082008-09-23 21:53:05

  0

non ha definito efficiente - il mio pensiero era che voleva un'identità non per la velocità, ma per la facilità d'uso. Ma se si tratta di una cosa da prestazioni, basta indicizzare una colonna esistente 23 set. 082008-09-23 23:19:48


5

commentato: non funziona se OldTable ha una colonna di identità.

penso che la tua risposta. #newtable ottiene automaticamente una colonna Identity da oldtable. Esegui le seguenti istruzioni:

create table oldtable (id int not null identity(1,1), v varchar(10)) 

select * into #newtable from oldtable 

use tempdb 
GO 
sp_help #newtable 

Ti mostra che #newtable ha la colonna Identity.

Se non si vuole che la colonna di identità, provare questo al momento della creazione di #newtable:

select id + 1 - 1 as nid, v, IDENTITY(int) as id into #newtable 
    from oldtable 

1

Buona domanda & Matt è stata una buona risposta.Per espandere sulla sintassi un po 'se la OldTable ha un'identità di un utente potrebbe eseguire il seguente:

SELECT col1, col2, IDENTITY(int) AS idcol 

    INTO #newtable 

    FROM oldtable 

-

Che sarebbe se il OldTable stato sceneggiato qualcosa come tale:

CREATE TABLE [dbo].[oldtable] 
(
    [oldtableID] [numeric](18, 0) IDENTITY(1,1) NOT NULL, 
    [col1] [nvarchar](50) NULL, 
    [col2] [numeric](18, 0) NULL, 
) 

Thx 4 informazioni a questa domanda mi ha aiutato,

Catto


2

Se vuoi includere la colonna che è l'identità corrente, puoi comunque farlo ma devi elencare esplicitamente le colonne e trasmettere l'identità corrente a un int (supponendo che sia uno ora), in questo modo:

select cast (CurrentID as int) as CurrentID, SomeOtherField, identity(int) as TempID 
into #temp 
from myserver.dbo.mytable 
  0

che funziona per me. Grazie 05 feb. 142014-02-05 17:57:34


0

Se dopo il *, si alias l'idcolumn che interrompe la query una seconda volta ... e gli diamo un nuovo nome ... inizia magicamente a funzionare.

Select Identity (int) AS RIF, *, Idsezione come Fix2IDs in #TempSections da Files_Sections