【问题标题】:Inserting dynamic pivot result into an existing table without knowing table definition在不知道表定义的情况下将动态透视结果插入现有表
【发布时间】:2014-02-22 00:13:22
【问题描述】:

我有一个动态数据透视表,它会在运行前生成未知数量的列。我正在尝试从现有表中清除数据并将查询结果插入其中。我遇到的问题是我不知道表定义会提前是什么,因为它是动态的。

这是我得到的错误:
Msg 213, Level 16, State 7, Line 1 Column name or number of supplied values does not match table definition.

透视列是一个日期列,可以有 1 个日期或 1000 多个日期。 如何创建与我尝试插入的数据匹配的表定义?

这是我的查询:

 DECLARE @colsPivot AS NVARCHAR(MAX),
 @colsUnpivot AS NVARCHAR(MAX),
 @query AS NVARCHAR(MAX)

select @colsPivot = STUFF((SELECT ',' + QUOTENAME(rce.EcoDate) 
                             from PhdRpt.RptCaseEco_542 AS rce
                             group by rce.EcoDate
                             order by rce.EcoDate
                     FOR XML PATH(''), TYPE
                     ).value('.', 'NVARCHAR(MAX)') 
                     ,1,1,'')

SELECT @colsUnpivot = stuff((SELECT ','+quotename(C.name)
FROM sys.columns AS C
WHERE C.object_id = object_id('PhdRpt.RptCaseEco_542') AND
C.name in ('NDCash', 'DCash')--LIKE '%Cash' or C.Name like  'NetGas'
FOR xml path('')), 1, 1, '')

set @query 
 = 'select *
 --into ##hello
 from
 (
     SELECT  
        ReportRunCaseId,
        col, 
        EcoDate,  
        val
    FROM PhdRpt.RptCaseEco_542  
unpivot
(
val
for col in ('+ @colsunpivot +')
) u
 ) x1
 pivot
 (
     max(val)
     for EcoDate in ('+ @colspivot +')
 ) p'

truncate table dbo.Table1
insert into dbo.Table1
exec(@query)

【问题讨论】:

    标签: sql sql-server exec truncate insert-into


    【解决方案1】:

    你可以这样做:

     DROP TABLE dbo.Table1
    
     DECLARE @colsPivot AS NVARCHAR(MAX),
     @colsUnpivot AS NVARCHAR(MAX),
     @query AS NVARCHAR(MAX)
    
    select @colsPivot = STUFF((SELECT ',' + QUOTENAME(rce.EcoDate) 
                                 from PhdRpt.RptCaseEco_542 AS rce
                                 group by rce.EcoDate
                                 order by rce.EcoDate
                         FOR XML PATH(''), TYPE
                         ).value('.', 'NVARCHAR(MAX)') 
                         ,1,1,'')
    
    SELECT @colsUnpivot = stuff((SELECT ','+quotename(C.name)
    FROM sys.columns AS C
    WHERE C.object_id = object_id('PhdRpt.RptCaseEco_542') AND
    C.name in ('NDCash', 'DCash')--LIKE '%Cash' or C.Name like  'NetGas'
    FOR xml path('')), 1, 1, '')
    
    set @query 
     = 'select *
     into dbo.Table1
     from
     (
         SELECT  
            ReportRunCaseId,
            col, 
            EcoDate,  
            val
        FROM PhdRpt.RptCaseEco_542  
    unpivot
    (
    val
    for col in ('+ @colsunpivot +')
    ) u
     ) x1
     pivot
     (
         max(val)
         for EcoDate in ('+ @colspivot +')
     ) p'
    
    exec(@query)
    

    【讨论】:

      【解决方案2】:

      我会 DROP 原始表并使用 SELECT INTO 子句即时创建新表。

      通过使用SELECT INTO,您无需事先创建表或担心它将有什么类型和多少列。 SQL Server 只会为您创建它。

      注意:这仅在表不存在时有效。

      有关INTO 子句http://technet.microsoft.com/en-us/library/ms188029.aspx 的完整文档

      作为另一种选择,您始终可以使用 SELECT INTO #temp 表,您可以删除或使用它来为您的其他表建模,但我认为这是您不想做的额外工作。

      【讨论】:

      • 谢谢。通过使用DROP,我能够清除旧数据并将新数据插入到同名表中。
      猜你喜欢
      • 2020-09-08
      • 2020-02-18
      • 2016-03-09
      • 2019-12-22
      • 2011-07-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多