在SQL Server中,我可以在添加列语句中创建一个具名的默认约束吗?

214
在SQL Server中,我在一张表上有一个新的列:
ALTER TABLE t_tableName 
    ADD newColumn NOT NULL

这个失败是因为我在没有指定默认约束的情况下指定了NOT NULL。表不应该有默认约束。
为了解决这个问题,我可以创建带有默认约束的表,然后再将其删除。
然而,似乎没有办法在此语句中指定默认约束的名称,所以我唯一的方法是编写一个存储过程,在sys.default_constraints表中查找它。
对于这种经常发生的操作来说,这样做有点混乱/冗长。有没有人有更好的解决方案?
5个回答

305

这应该可以正常工作:

ALTER TABLE t_tableName 
    ADD newColumn VARCHAR(50)
    CONSTRAINT YourContraintName DEFAULT '' NOT NULL

1
也适用于2012年。详细信息请参阅:http://msdn.microsoft.com/zh-cn/library/ms187742.aspx - adam77
28
为什么不将NOT NULL放在数据类型旁边呢?尽管将其放在约束条件之后在语法上是有效的,但是这样做似乎会令人感到困惑。 - Tullo_x86
1
@Tullo_x86 在SSMS和SSDT中,“生成脚本…”工具仍然默认将NOT NULL部分放在类型、默认约束和时间表GENERATED位之后的最后。这太丑陋了。 - Dai

143
ALTER TABLE t_tableName 
    ADD newColumn int NOT NULL
        CONSTRAINT DF_defaultvalue DEFAULT (1)

29
我更喜欢这个答案,因为我可以删除默认约束,而不必担心失去非空约束。 - EleventhDoctor
13
这句话的意思是:这没有任何意义。 NOT NULL不是约束的一部分,而且DROP语句只是参考了约束名称。 - Roger Willcocks
16
您说得对,但仅仅阅读一下就会更清楚,NOT NULL 是独立于约束的。 - deluxxxe

55

我想要添加一些细节:

最重要的提示是:您绝对不能创建没有明确名称的约束!

未命名约束面临的最大问题:当您在不同的客户机上执行此操作时,每个客户机都会得到不同/随机的名称
任何将来的升级脚本都将是一个真正的头疼…

一般建议为:

  • 不要使用没有名称的约束!
  • 使用一些命名约定,例如:
    • DF_TableName_ColumnName 用于默认约束
    • CK_TableName_ColumnName 用于检查约束
    • UQ_TableName_ColumnName 用于唯一约束
    • PK_TableName 用于主键约束

一般语法为:

TheColumn <DataType> Nullability CONSTRAINT ConstraintName <ConstraintType> <ConstraintDetails>

试试这个

你可以向每个列添加更多的限制条件,就像你在逗号后添加列一样,你也可以添加其他的限制条件:

CREATE TABLE dbo.SomeOtherTable(TheIdThere INT NOT NULL CONSTRAINT PK_SomeOtherTable PRIMARY KEY)
GO
CREATE TABLE dbo.TestTable
(
 --define the primary key
 ID INT IDENTITY NOT NULL CONSTRAINT PK_TestTable PRIMARY KEY

 --let the string be unique (results in a unique index implicitly)
,SomeUniqueString VARCHAR(100) NOT NULL CONSTRAINT UQ_TestTable_SomeUniqueString UNIQUE

 --define two constraints, one for a default value and one for a value check
,SomeNumber INT NULL CONSTRAINT DF_TestTable_SomeNumber DEFAULT (0)
                     CONSTRAINT CK_TestTable_SomeNumber_gt100 CHECK(SomeNumber>100)

 --add a foreign key constraint
,SomeFK INT NOT NULL CONSTRAINT FK_TestTable_SomeFK FOREIGN KEY REFERENCES dbo.SomeOtherTable(TheIdThere)

 --add a constraint for two columns separately
,CONSTRAINT UQ_TestTable_StringAndNumber UNIQUE(SomeFK,SomeNumber)
);
GO

--插入一些数据

INSERT INTO dbo.SomeOtherTable VALUES(1);
INSERT INTO dbo.TestTable(SomeUniqueString,SomeNumber,SomeFK) VALUES('hello',111,1);
GO
INSERT INTO dbo.TestTable(SomeUniqueString,SomeNumber,SomeFK) 
VALUES('fails due to uniqueness of 111,1',111,1);

前两个答案都列出了它们的约束条件,因此你的陈述“我想添加一些细节,因为现有的答案相当简略:最重要的提示是:你绝不能创建一个没有明确名称的约束条件!”似乎有些多余。 - Mitch Wheat

2
试试以下脚本——
ALTER TABLE DEMO_TABLE
ADD Column1 INT CONSTRAINT Def_Column1 DEFAULT(3) NOT NULL,
    Column2 VARCHAR(10) CONSTRAINT Def_Column2 DEFAULT('New') NOT NULL;
GO

-1

当我向大表添加新列和默认值时,我使用以下方法。请逐行执行:

ALTER TABLE dbo.[TableName] ADD [ColumnName] BIT NULL; /*null>no table rebuild*/

UPDATE rf SET rf.[ColumnName] = 0 FROM dbo.[TableName] rf WHERE rf.[ColumnName] IS NULL;

ALTER TABLE dbo.[TableName] ALTER COLUMN [ColumnName] BIT NOT NULL;

ALTER TABLE dbo.[TableName] ADD CONSTRAINT DF_[TableName]_[ColumnName] DEFAULT 0 FOR [ColumnName];

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接