将具有默认值的列添加到SQL Server中的现有表


Answers:


3497

句法:

ALTER TABLE {TABLENAME} 
ADD {COLUMNNAME} {TYPE} {NULL|NOT NULL} 
CONSTRAINT {CONSTRAINT_NAME} DEFAULT {DEFAULT_VALUE}
WITH VALUES

例:

ALTER TABLE SomeTable
        ADD SomeCol Bit NULL --Or NOT NULL.
 CONSTRAINT D_SomeTable_SomeCol --When Omitted a Default-Constraint Name is autogenerated.
    DEFAULT (0)--Optional Default-Constraint.
WITH VALUES --Add if Column is Nullable and you want the Default Value for Existing Records.

笔记:

可选的约束名称:
如果省略,CONSTRAINT D_SomeTable_SomeColSQL Server将自动生成
    一个带有有趣名称的Default-Contraint,例如:DF__SomeTa__SomeC__4FB7FEF6

可选的值声明:
WITH VALUES当你的列可以为空时,才需要
    和想要的价值用于现有记录的默认值。
如果您的Column是NOT NULL,则
    无论您是否指定,它都会自动对所有现有记录使用默认值WITH VALUES

插入如何与默认约束一起使用:
如果将记录插入到SomeTable并且指定SomeCol的值,则它将默认为0
如果您插入一个Record 并将其SomeCol值指定为NULL(并且您的列允许为空),
    则将使用Default-Constraint ,NULL并将其作为Value插入。

注释基于以下每个人的好评。
特别感谢:
    @ Yatrix,@ WalterStabosz,@ YahooSerious和@StackMan的评论。


332
请记住,如果该列可为空,则null将是用于现有行的值。
理查德·科莱特

17
@Thecrocodilehunter Nullable列意味着您可以为列值插入Null。如果它不是可为空的列,则必须插入该数据类型的某些值。因此,对于现有记录,将在其中插入Null,在新记录中,除非另外指定,否则将插入默认值。合理?
Yatrix 2012年

41
我喜欢这个答案比dbugger更好,因为它明确命名了默认约束。仍然使用dbugger的语法创建默认约束,但其名称是自动生成的。在编写DROP-CREATE脚本时,知道确切的名称很方便。
Walter Stabosz 2012年

18
@Vertigo仅当列为时才为真NOT NULL。请尝试以下操作:create table blah(a int not null primary key clustered); insert blah values (1), (2); alter table blah add b int null constraint df_blah_b default (0); select * from blah;您将看到column的2个NULL值b
ErikE 2013年

48
使用WITH VALUES更新现有的可空行。请参见MSDN:“如果添加的列允许空值并WITH VALUES已指定,则默认值存储在新列中,并添加到现有行中。”
雅虎严重2014年

1008
ALTER TABLE Protocols
ADD ProtocolTypeID int NOT NULL DEFAULT(1)
GO

包含DEFAULT将使用默认值填充现有行中的列,因此不会违反NOT NULL约束。


13
该答案的问题在于默认值仅对新记录有效。现有记录仍将具有NULL值。
Roee Gavirel

130
您会发现情况并非如此。否则将违反约束。
dbugger 2011年

35
现有行中的列将填充默认值。一点经验检验将证明这一点。
dbugger 2011年

80
只是要澄清一下-如果命令中省略了“ NOT NULL”,则现有行的值将不会更新,并将保持NULL。如果命令中包含“ NOT NULL”,则将更新现有行的值以匹配默认值。
Stack Man

15
对于多个列 ALTER TABLE table_1 ADD col_1 int NOT NULL DEFAULT(1),col_2 int NULL
2013年

233

添加null的列时WITH VALUES将确保将特定的DEFAULT值应用于现有行:

ALTER TABLE table
ADD column BIT     -- Demonstration with NULL-able column added
CONSTRAINT Constraint_name DEFAULT 0 WITH VALUES

13
这是关键。容易假设具有DEFAULT约束的列将始终具有值-即使NOT NULL未指定,也不能为NULL 。
Bill Brinkley,2012年

6
@tkocmathla嗯,我不是在谈论BIT数据类型,而是在谈论这个特殊的BIT 专栏。查看答案,该列声明为NOT NULL
rsenna 2014年

136
ALTER TABLE <table name> 
ADD <new column name> <data type> NOT NULL
GO
ALTER TABLE <table name> 
ADD CONSTRAINT <constraint name> DEFAULT <default value> FOR <new column name>
GO

7
如果表已具有内容,则此方法将不起作用,因为新的“不可为空”列是在默认值约束之前创建的
WDuffy 2016年

129
ALTER TABLE MYTABLE ADD MYNEWCOLUMN VARCHAR(200) DEFAULT 'SNUGGLES'

13
此添加null!之前必须不为null
baaroz 2013年

5
@baaroz,此作品与NOT NULL:ALTER TABLE MYTABLE ADD MYNEWCOLUMN VARCHAR(200)NOT NULL DEFAULT '挨近'
shaijut

100

当您添加的列有NOT NULL约束但没有DEFAULT约束(值)时要当心。ALTER TABLE如果表中有任何行,则该语句将失败。解决方案是NOT NULL从新列中删除约束,或者为其提供DEFAULT约束。


2
关于它的任何SQL示例吗?
Kiquenet '16

98

最基本的版本只有两行

ALTER TABLE MyTable
ADD MyNewColumn INT NOT NULL DEFAULT 0

81

采用:

-- Add a column with a default DateTime  
-- to capture when each record is added.

ALTER TABLE myTableName  
ADD RecordAddedDate SMALLDATETIME NULL DEFAULT (GETDATE())  
GO 

79

如果要添加多个列,可以使用这种方式,例如:

ALTER TABLE YourTable
    ADD Column1 INT NOT NULL DEFAULT 0,
        Column2 INT NOT NULL DEFAULT 1,
        Column3 VARCHAR(50) DEFAULT 'Hello'
GO


54

要将列添加为具有默认值的现有数据库表,我们可以使用:

ALTER TABLE [dbo.table_name]
    ADD [Column_Name] BIT NOT NULL
Default ( 0 )

这是用默认值向现有数据库表添加列的另一种方法。

下面是一个更详尽的SQL脚本,用于添加具有默认值的列,包括在添加列之前检查该列是否存在,还签入约束,如果存在约束则将其删除。该脚本还为约束命名,因此我们可以有一个很好的命名约定(我喜欢DF_),否则,SQL将为我们提供一个约束,该约束的名称具有随机生成的数字。因此也可以命名约束,这很好。

-------------------------------------------------------------------------
-- Drop COLUMN
-- Name of Column: Column_EmployeeName
-- Name of Table: table_Emplyee
--------------------------------------------------------------------------
IF EXISTS (
            SELECT 1
            FROM INFORMATION_SCHEMA.COLUMNS
            WHERE TABLE_NAME = 'table_Emplyee'
              AND COLUMN_NAME = 'Column_EmployeeName'
           )
    BEGIN

        IF EXISTS ( SELECT 1
                    FROM sys.default_constraints
                    WHERE object_id = OBJECT_ID('[dbo].[DF_table_Emplyee_Column_EmployeeName]')
                      AND parent_object_id = OBJECT_ID('[dbo].[table_Emplyee]')
                  )
            BEGIN
                ------  DROP Contraint

                ALTER TABLE [dbo].[table_Emplyee] DROP CONSTRAINT [DF_table_Emplyee_Column_EmployeeName]
            PRINT '[DF_table_Emplyee_Column_EmployeeName] was dropped'
            END
     --    -----   DROP Column   -----------------------------------------------------------------
        ALTER TABLE [dbo].table_Emplyee
            DROP COLUMN Column_EmployeeName
        PRINT 'Column Column_EmployeeName in images table was dropped'
    END

--------------------------------------------------------------------------
-- ADD  COLUMN Column_EmployeeName IN table_Emplyee table
--------------------------------------------------------------------------
IF NOT EXISTS (
                SELECT 1
                FROM INFORMATION_SCHEMA.COLUMNS
                WHERE TABLE_NAME = 'table_Emplyee'
                  AND COLUMN_NAME = 'Column_EmployeeName'
               )
    BEGIN
    ----- ADD Column & Contraint
        ALTER TABLE dbo.table_Emplyee
            ADD Column_EmployeeName BIT   NOT NULL
            CONSTRAINT [DF_table_Emplyee_Column_EmployeeName]  DEFAULT (0)
        PRINT 'Column [DF_table_Emplyee_Column_EmployeeName] in table_Emplyee table was Added'
        PRINT 'Contraint [DF_table_Emplyee_Column_EmployeeName] was Added'
     END

GO

这是使用默认值将列添加到现有数据库表中的两种方法。


52

您可以通过以下方式使用T-SQL进行操作。

 ALTER TABLE {TABLENAME}
 ADD {COLUMNNAME} {TYPE} {NULL|NOT NULL}
 CONSTRAINT {CONSTRAINT_NAME} DEFAULT {DEFAULT_VALUE}

您还可以通过右键单击“设计”菜单中的表格,将默认值设置为表格来使用SQL Server Management Studio

此外,如果要将同一列(如果不存在)添加到数据库中的所有表,请使用:

 USE AdventureWorks;
 EXEC sp_msforeachtable
'PRINT ''ALTER TABLE ? ADD Date_Created DATETIME DEFAULT GETDATE();''' ;

50

在SQL Server 2008-R2中,我进入设计模式-在测试数据库中-使用设计器添加我的两列,并使用GUI进行设置,然后臭名昭著的Right-Click提供选项“ Generate Change Script” ”!

您猜对了,Bang up弹出一个小窗口,其中包含格式正确的保证工作更改脚本。点击轻松按钮。


48

另外,您可以添加默认值而不必显式命名约束:

ALTER TABLE [schema].[tablename] ADD  DEFAULT ((0)) FOR [columnname]

如果在创建此约束时现有的默认约束存在问题,则可以通过以下方式将其删除:

alter table [schema].[tablename] drop constraint [constraintname]

1
仅供参考,为了便于维护,使用标准命名方案(例如“ DF_Table_Column”)显式命名约束。否则,定位约束需要更多的工作。
Mike Christian

43

这也可以在SSMS GUI中完成。我在下面显示默认日期,但是默认值可以是任意值。

  1. 将表置于设计视图中(在对象资源管理器->设计中右键单击表)
  2. 在表中添加一列(如果已经存在,请单击要更新的列)
  3. 在下面的“列属性”中,在“ 默认值”或“绑定”字段中输入(getdate())或,abc或输入0任何您想要的,如下图所示:

在此处输入图片说明



31

例:

ALTER TABLE [Employees] ADD Seniority int not null default 0 GO


22

首先创建一个名称为student的表:

CREATE TABLE STUDENT (STUDENT_ID INT NOT NULL)

在其中添加一列:

ALTER TABLE STUDENT 
ADD STUDENT_NAME INT NOT NULL DEFAULT(0)

SELECT * 
FROM STUDENT

将创建该表,并将一列添加到具有默认值的现有表中。

图片1


19

这有很多答案,但是我觉得需要添加此扩展方法。这似乎需要更长的时间,但是如果您要向活动数据库中具有数百万行的表中添加NOT NULL字段,这将非常有用。

ALTER TABLE {schemaName}.{tableName}
    ADD {columnName} {datatype} NULL
    CONSTRAINT {constraintName} DEFAULT {DefaultValue}

UPDATE {schemaName}.{tableName}
    SET {columnName} = {DefaultValue}
    WHERE {columName} IS NULL

ALTER TABLE {schemaName}.{tableName}
    ALTER COLUMN {columnName} {datatype} NOT NULL

这样做是将列添加为可为空的字段,并使用默认值,将所有字段更新为默认值(或者您可以分配更多有意义的值),最后它将更改该列为NOT NULL。

这样做的原因是,如果您更新了一个大型表并添加了一个新的非null字段,它必须写入到每一行,从而在添加列并写入所有值时将锁定整个表。

此方法将添加可为空的列,该列可单独运行得快得多,然后在设置非空状态之前填充数据。

我发现在一条语句中完成全部操作会在4至8分钟内将我们活动较多的表之一锁定,而且我经常杀死了该过程。这种方法每个部分通常只需要几秒钟的时间,并且将锁定降至最低。

此外,如果您有一个数十亿行的表,那么可能值得批量更新,如下所示:

WHILE 1=1
BEGIN
    UPDATE TOP (1000000) {schemaName}.{tableName}
        SET {columnName} = {DefaultValue}
        WHERE {columName} IS NULL

    IF @@ROWCOUNT < 1000000
        BREAK;
END


18

SQL Server +更改表+添加列+默认值uniqueidentifier

ALTER TABLE Product 
ADD ReferenceID uniqueidentifier not null 
default (cast(cast(0 as binary) as uniqueidentifier))

18
IF NOT EXISTS (
    SELECT * FROM INFORMATION_SCHEMA.COLUMNS
    WHERE TABLE_NAME ='TABLENAME' AND COLUMN_NAME = 'COLUMNNAME'
)
BEGIN
    ALTER TABLE TABLENAME ADD COLUMNNAME Nvarchar(MAX) Not Null default
END

3
NOT EXISTS在尝试更改表格之前,我喜欢检查。很好的解决方案。关于此工作原理的其他一些评论将使其变得更加有用。
Michael Gaskill 2016年

17
--Adding Value with Default Value
ALTER TABLE TestTable
ADD ThirdCol INT NOT NULL DEFAULT(0)
GO

也许用实际代码替换图像?很难按原样复制和粘贴。
David Faber

6
与几年前已经存在的答案相比,这没有任何价值。
nvoigt

14

将新列添加到表中:

ALTER TABLE [table]
ADD Column1 Datatype

例如,

ALTER TABLE [test]
ADD ID Int

如果用户想使其自动递增,则:

ALTER TABLE [test]
ADD ID Int IDENTITY(1,1) NOT NULL

13

这适用于SQL Server:

ALTER TABLE TableName
ADD ColumnName (type) -- NULL OR NOT NULL
DEFAULT (default value)
WITH VALUES

例:

ALTER TABLE Activities
ADD status int NOT NULL DEFAULT (0)
WITH VALUES

如果要添加约束,则:

ALTER TABLE Table_1
ADD row3 int NOT NULL
CONSTRAINT CONSTRAINT_NAME DEFAULT (0)
WITH VALUES

7
与几年前已经存在的答案相比,这没有任何价值。
nvoigt

11

这可以通过以下代码完成。

CREATE TABLE TestTable
    (FirstCol INT NOT NULL)
    GO
    ------------------------------
    -- Option 1
    ------------------------------
    -- Adding New Column
    ALTER TABLE TestTable
    ADD SecondCol INT
    GO
    -- Updating it with Default
    UPDATE TestTable
    SET SecondCol = 0
    GO
    -- Alter
    ALTER TABLE TestTable
    ALTER COLUMN SecondCol INT NOT NULL
    GO



9

好吧,现在我对以前的答案做了一些修改。我注意到没有任何答案IF NOT EXISTS。所以我将提供一个新的解决方案,因为我在更换桌子时遇到了一些问题。

IF NOT EXISTS (SELECT * FROM INFORMATION_SCHEMA.columns WHERE table_name = 'TaskSheet' AND column_name = 'IsBilledToClient')
BEGIN
ALTER TABLE dbo.TaskSheet ADD
 IsBilledToClient bit NOT NULL DEFAULT ((1))
END
GO

TaskSheet是特定的表名,IsBilledToClient是要插入的新列以及1默认值。这意味着在新列中将是现有行的值,因此将在此处自动设置一个值。但是,您可以根据需要更改列类型,就像我使用过的那样BIT,因此我将默认值设置为1。

我建议使用上述系统,因为我遇到了问题。那是什么问题呢?问题是,如果IsBilledToClient表表中确实存在该列,那么,如果仅执行下面给出的部分代码,则会在“ SQL Server查询”构建器中看到错误。但是,如果它不存在,那么在执行时将第一次没有错误。

ALTER TABLE {TABLENAME}
ADD {COLUMNNAME} {TYPE} {NULL|NOT NULL}
CONSTRAINT {CONSTRAINT_NAME} DEFAULT {DEFAULT_VALUE}
[WITH VALUES]
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.