SQL Server 中的数据透视表查询

Posted

技术标签:

【中文标题】SQL Server 中的数据透视表查询【英文标题】:Pivot table query in SQL Server 【发布时间】:2015-12-02 05:28:48 【问题描述】:

我有如下所示的表格。我需要获取与每个不同元素的最大日期时间戳相对应的值,并使用 SQL Server 2005 或更高版本将行转换为列。列名值(即 A1、A2、A3 列是动态的,可以根据可用数据进行更改)

基表(来自结果查询)

Id  Name    Value   DateTimeStamp
--------------------------------------
1   A1  5   Nov 14 2011 03:12:12:947PM
1   A1  6   Nov 15 2011 03:12:12:947PM
1   A2  7   Nov 14 2011 03:12:12:947PM
1   A2  8   Nov 15 2011 03:12:12:947PM
1   A3  9   Nov 14 2011 03:12:12:947PM
2   A3  10  Nov 15 2011 03:12:12:947PM
2   A1  1   Nov 14 2011 03:12:12:947PM
2   A1  2   Nov 15 2011 03:12:12:947PM
2   A2  3   Nov 14 2011 03:12:12:947PM
2   A2  4   Nov 15 2011 03:12:12:947PM
2   A3  5   Nov 14 2011 03:12:12:947PM
2   A3  6   Nov 15 2011 03:12:12:947PM

期望的输出:

Id  A1  A2  A3
---------------
1   6   8   10
2   2   4   6

【问题讨论】:

名称列的值数量是否有限?另外,DateTimeStamp 列的数据类型是什么? 抱歉,列名也是动态的。 [T-SQL 动态数据透视] 的可能重复项。 (***.com/questions/12210692/t-sql-dynamic-pivot) 请注意,您需要将数据透视结果加入到表中以获取对应于最大日期时间的值。 不想使用动态查询。使用静态查询的任何可用解决方案。 您有许多事先不知道的值。您希望静态查询如何工作? 【参考方案1】:

您可以使用dynamic crosstab: 来做到这一点

SQL Fiddle

DECLARE @sql NVARCHAR(MAX) = ''

SELECT @sql =
'SELECT
    Id' + CHAR(10)

SELECT @sql = @sql +
    ', MAX(CASE WHEN Name = ''' + Name +  ''' THEN Value END) AS ' + QUOTENAME(Name) + CHAR(10)
FROM (SELECT DISTINCT Name FROM tbl) t
ORDER BY Name

SELECT @sql = @sql +
'FROM (
    SELECT *,
        RN = ROW_NUMBER() OVER(PARTITION BY Id, Name ORDER BY DateTimeStamp DESC)
    FROM tbl
) t
WHERE Rn = 1
GROUP BY Id
ORDER BY Id'

EXEC sp_executesql @sql

【讨论】:

不使用动态查询的任何可能的解决方案。问题是我需要将结果加入另一个子查询。非常感谢您的努力。谢谢。 由于Names 的数量未知,如果不使用动态 SQL,您将无法做到这一点。 您可以尝试将结果插入到临时表中。

以上是关于SQL Server 中的数据透视表查询的主要内容,如果未能解决你的问题,请参考以下文章

Microsoft Access 数据透视表到 SQL Server 数据透视表

Sql Server 聚合或数据透视表查询

SQL Server 中具有动态列的数据透视表

MS SQL Server 中的动态数据透视

列子句中带有子查询的 MS SQL Server 数据透视表

没有聚合函数的 SQL Server 数据透视查询