将所有 float 类型的列动态转换为 decimal

Dynamically converting all float type columns to decimal

我需要将特定数据库中所有 table 中的所有浮点数据类型列精确转换为十进制。

我有以下代码:

DECLARE @sql VARCHAR(8000)

SELECT 
    @sql = COALESCE(@sql + ',', '') + 
           CASE DATA_TYPE 
              WHEN 'float' THEN 'CAST(' + COLUMN_NAME  + ' AS DECIMAL(28, 10))'
              ELSE COLUMN_NAME
           END
FROM
    INFORMATION_SCHEMA.COLUMNS
WHERE 
    DATA_TYPE = 'float'

EXEC ('SELECT '+ @sql + ' FROM TABLE_NAME')

我还有一个以小数刻度为变量的版本:

DECLARE 
    @sql NVARCHAR(MAX),
    @DecimalPlace INT = 10

SELECT
    @sql = COALESCE(@sql + ',', '') + 
           CASE DATA_TYPE 
              WHEN 'float' 
                 THEN 'CAST(' + COLUMN_NAME  + ' AS DECIMAL(28, ' + CAST(@DecimalPlace AS NVARCHAR) + '))'
                 ELSE COLUMN_NAME
           END
FROM
    INFORMATION_SCHEMA.COLUMNS
WHERE 
    DATA_TYPE = 'float'

EXEC ('SELECT '+ @sql + ' FROM TABLE_NAME')

我的最顶层脚本目前出现以下错误:

Msg 156, Level 15, State 1, Line 1
Incorrect syntax near the keyword 'from'.

我看到了我的问题...'from TABLE_NAME' 无效。这是生成的 SQL...

SELECT
    CAST(DWF_ORDERS_EXCHANGE_RATE_DOL AS DECIMAL(28,10)),
    CAST(DWF_ORDERS_ITEM_DISCOUNT_PRC AS DECIMAL(28,10)),
    CAST(DWF_ORDERS_SALES_QTY AS DECIMAL(28,10)),
    CAST(DWF_ORDERS_OPEN_QTY 
FROM
    TABLE_NAME 

看来我的逻辑一次只能容纳一个 table。是否有一种相对简单的方法来修改我的逻辑以适应多个 table 被输入到一个变量中?

此外,如果适用,我不确定要保持原始浮动 precision/scale 的最佳做法是什么。

使用 SQL Server 2014。

以下脚本将使用浮点列遍历所有 table,并生成具有正确 table 名称的动态 SQL:

declare @Table table ([Name] nvarchar(max), Handled bit default(0));
declare @Sql nvarchar(max), @TableName nvarchar(max);

insert into @Table ([Name])
  select TABLE_NAME
  from INFORMATION_SCHEMA.COLUMNS
  where DATA_TYPE = 'float'
  group by TABLE_NAME;

while exists (select 1 from @Table where Handled = 0) begin
  select top 1 @TableName = [Name] from @Table where Handled = 0;

  select @Sql = coalesce(@sql+',','') + 
    case DATA_TYPE 
    when 'float' then 'cast(' + COLUMN_NAME  + ' as decimal(28,10))'
    else COLUMN_NAME
    end
  from INFORMATION_SCHEMA.COLUMNS
  where DATA_TYPE = 'float' and TABLE_NAME = @TableName;

  set @Sql = 'select '+ @Sql + ' from ' + @TableName;

  print(@Sql);
  --exec (@Sql);

  update @Table set Handled = 1 where @TableName = [Name];
end