J'ai une table table1
dans SQL Server 2008 et elle contient des enregistrements.
Je veux que la colonne de clé primaire table1_Sno
soit une colonne à incrémentation automatique. Cela peut-il être fait sans transfert de données ni clonage de table?
Je sais que je peux utiliser ALTER TABLE pour ajouter une colonne à incrémentation automatique, mais puis-je simplement ajouter l'option AUTO_INCREMENT à une colonne existante qui est la clé primaire?
La modification de la propriété IDENTITY
est en réalité un changement de métadonnées uniquement. Mais pour mettre à jour les métadonnées directement, il faut démarrer l'instance en mode mono-utilisateur et déconner avec certaines colonnes de sys.syscolpars
et n'est pas documenté/non pris en charge et ce n'est pas quelque chose que je recommanderais ou donnerais de plus amples détails.
Pour les personnes rencontrant cette réponse sur SQL Server 2012+, le moyen le plus simple d'obtenir ce résultat pour une colonne à incrémentation automatique serait de créer un objet SEQUENCE
et de définir le next value for seq
comme colonne par défaut.
Alternativement, ou pour les versions précédentes (à partir de 2005), la solution de contournement publiée sur cet élément de connexion montre une méthode complètement prise en charge, sans avoir besoin de la taille des opérations de données à l'aide de ALTER TABLE...SWITCH
. Également blogué à propos de MSDN ici . Bien que le code permettant d'y parvenir ne soit pas très simple et qu'il existe des restrictions - par exemple, la table en cours de modification ne peut pas être la cible d'une contrainte de clé étrangère.
identity
.CREATE TABLE dbo.tblFoo
(
bar INT PRIMARY KEY,
filler CHAR(8000),
filler2 CHAR(49)
)
INSERT INTO dbo.tblFoo (bar)
SELECT TOP (10000) ROW_NUMBER() OVER (ORDER BY (SELECT 0))
FROM master..spt_values v1, master..spt_values v2
identity
(plus ou moins instantanée).BEGIN TRY;
BEGIN TRANSACTION;
/*Using DBCC CHECKIDENT('dbo.tblFoo') is slow so use dynamic SQL to
set the correct seed in the table definition instead*/
DECLARE @TableScript nvarchar(max)
SELECT @TableScript =
'
CREATE TABLE dbo.Destination(
bar INT IDENTITY(' +
CAST(ISNULL(MAX(bar),0)+1 AS VARCHAR) + ',1) PRIMARY KEY,
filler CHAR(8000),
filler2 CHAR(49)
)
ALTER TABLE dbo.tblFoo SWITCH TO dbo.Destination;
'
FROM dbo.tblFoo
WITH (TABLOCKX,HOLDLOCK)
EXEC(@TableScript)
DROP TABLE dbo.tblFoo;
EXECUTE sp_rename N'dbo.Destination', N'tblFoo', 'OBJECT';
COMMIT TRANSACTION;
END TRY
BEGIN CATCH
IF XACT_STATE() <> 0 ROLLBACK TRANSACTION;
PRINT ERROR_MESSAGE();
END CATCH;
INSERT INTO dbo.tblFoo (filler,filler2)
OUTPUT inserted.*
VALUES ('foo','bar')
bar filler filler2
----------- --------- ---------
10001 foo bar
DROP TABLE dbo.tblFoo
Cette stratégie copie physiquement les lignes deux fois environ, ce qui peut prendre beaucoup plus de temps si la table que vous copiez est très grande.
Vous pouvez sauvegarder vos données, supprimer et reconstruire la table avec l'incrémentation automatique et la clé primaire, puis recharger les données.
Je vais vous guider avec un exemple:
Étape 1, créer une table foobar (sans clé primaire ni incrémentation automatique):
CREATE TABLE foobar(
id int NOT NULL,
name nchar(100) NOT NULL,
)
Étape 2, insérez quelques lignes
insert into foobar values(1, 'one');
insert into foobar values(2, 'two');
insert into foobar values(3, 'three');
Étape 3, copier les données foobar dans une table temporaire:
select * into temp_foobar from foobar
Étape 4, déposer la table foobar:
drop table foobar;
Étape 5, recréez votre table avec les propriétés de clé primaire et d'incrémentation automatique:
CREATE TABLE foobar(
id int primary key IDENTITY(1, 1) NOT NULL,
name nchar(100) NOT NULL,
)
Étape 6, insérez vos données de la table temporaire dans foobar
SET IDENTITY_INSERT temp_foobar ON
INSERT into foobar (id, name) select id, name from temp_foobar;
Étape 7, supprimez votre table temporaire et vérifiez si cela a fonctionné:
drop table temp_foobar;
select * from foobar;
Vous devriez l'obtenir, et lorsque vous inspectez la table foobar, la colonne id est incrémentée automatiquement de 1 et id est une clé primaire:
1 one
2 two
3 three
Si vous souhaitez le faire via le concepteur, vous pouvez le faire en suivant les instructions ici "Enregistrer les modifications n'est pas autorisé" lors de la modification d'une colonne existante pour qu'elle soit Null -
Oui, vous pouvez. Allez dans Outils> Designers> Table et Designers et décochez "Empêcher l'enregistrement des modifications empêchant la création de tables" .
Si vous ne souhaitez pas ajouter de nouvelle colonne et que vous pouvez garantir que votre colonne int actuelle est unique, vous pouvez sélectionner toutes les données dans une table temporaire, supprimer la table et la recréer avec la colonne IDENTITY spécifiée. Ensuite, en utilisant SET IDENTITY INSERT ON
, vous pouvez insérer toutes vos données de la table temporaire dans la nouvelle table.
Non, vous ne pouvez pas ajouter d’option d’incrémentation automatique à une colonne existante contenant des données. Je pense que l’option que vous avez mentionnée est la meilleure.
Regardez ici .
Le script ci-dessous peut être une bonne solution. Travaillé également dans des données volumineuses.
ALTER DATABASE WMlive SET RECUPERER SIMPLE AVEC NO_WAIT
ALTER TABLE WMBOMTABLE DROP CONSTRAINT PK_WMBomTable
ALTER TABLE WMBOMTABLE colonne de dépôt BOMID
ALTER TABLE WMBOMTABLE ADD BomID int IDENTITY (1, 1) NON NUL;
ALTER TABLE WMBOMTABLE AJOUTER UN CONTRAINT PK_WMBomTable PRIMARY KEY CLUSTERED (BomID);
ALTER DATABASE WMlive SET RÉCUPÉRATION PLEINE AVEC NO_WAIT