【问题标题】:Changing all varchar columns in a SQL Server database to nvarchar将 SQL Server 数据库中的所有 varchar 列更改为 nvarchar
【发布时间】:2016-12-23 17:36:26
【问题描述】:

我正在尝试将数据库中的所有 varchar 列更新为 nvarchar 而不会丢失数据。

我有以下疑问:

select * 
from INFORMATION_SCHEMA.COLUMNS 
where DATA_TYPE = 'varchar'

如何修改它以更新它找到的列并将其反映在整个数据库中?

【问题讨论】:

  • 你不这样做,你必须创建一个新表,迁移数据并删除原始数据。

标签: sql sql-server sql-server-2008 sql-server-2012


【解决方案1】:

我会使用 SQL Server 特定的sys 目录视图,而我要做的只是简单地创建 更改这些数据类型所需的 T-SQL 语句 - 如下所示:

SELECT
    t.name, s.name, c.name,
    'ALTER TABLE ' + s.name + '.' + t.Name + ' ALTER COLUMN ' + c.name + ' NVARCHAR(' + 
        CASE 
            WHEN c.max_length = -1 THEN 'MAX'
            WHEN c.max_length > 4000 THEN 'MAX'
            ELSE CAST(c.max_length AS VARCHAR(10))
        END
    +
    CASE WHEN c.is_nullable = 1 THEN ');'
         ELSE ') NOT NULL;'
    END
FROM
    sys.tables t
INNER JOIN 
    sys.schemas s ON t.schema_id = s.schema_id
INNER JOIN 
    sys.columns c ON c.object_id = t.object_id
INNER JOIN 
    sys.types ty ON c.system_type_id = ty.system_type_id
WHERE
    ty.name = 'VARCHAR'
    AND c.is_computed = 0

AdventureWorks 数据库上运行,这将输出如下内容:

ALTER TABLE Sales.SalesOrderHeader ALTER COLUMN CreditCardApprovalCode NVARCHAR(15);
ALTER TABLE Person.Password ALTER COLUMN PasswordHash NVARCHAR(128);
ALTER TABLE Person.Password ALTER COLUMN PasswordSalt NVARCHAR(10);

然后您可以将其从输出网格复制到新的查询窗口并执行。

注意:AdventureWorks 运行您的原始脚本告诉我,在这种情况下,其中一列是计算的,因此不能通过简单地使用ALTER TABLE ... ALTER COLUMN .... 声明 - 这就是我在此处显示的脚本中排除计算列的原因。

如果你真的坚持,你也可以把我的这条SQL语句变成游标的“心脏”,然后遍历T-SQL语句来修改表,并执行那些使用EXEC(...)EXEC sp_executesql

【讨论】:

  • +1 用于捕获计算列问题。目前需要一个小更新来处理(max) 长度,返回NVARCHAR(-1)
  • 非常好的答案!
  • @SqlZim:添加了对处理VARCHAR(MAX) 案例的支持
  • 改变CASE c.max_length条件:CASE WHEN c.max_length >4000 OR c.max_length < 0 THEN 'max' ELSE CAST(c.max_length as varchar(5)) + ');'
猜你喜欢
  • 2021-06-10
  • 1970-01-01
  • 1970-01-01
  • 2010-09-15
  • 2016-11-11
  • 2011-12-30
  • 1970-01-01
  • 1970-01-01
  • 2017-11-08
相关资源
最近更新 更多