在这个问题重复结束之前,我已经在SO上看到了很多"SQL动态数据透视表"的例子,但到目前为止我所尝试的都没有奏效。许多使用PIVOT的示例都需要SUM或MAX值。我没有这些。
我有一个单表SQL Server数据库。
该表包含产品和相关属性。你可能会争辩说这些房产应该分为一张单独的表,但我坚持我所拥有的。。1张表。
示例表(tblObject(:
prodId | fieldName | fieldValue |
---|---|---|
ABC123 | 名称 | 工具1|
ABC123 | 描述 | 很棒的小部件 |
ABC123 | 状态 | 留//tr>|
XYZ999 | 名称 | 工具9[/tr>|
XYZ999 | 描述 | 可爱的小部件 |
XYZ999 | 状态 | 动//tr>
我认为您不太了解聚合函数如何影响数据透视值。它们应该只按照其他值(在您的例子中是prodID(进行分组。
让我们模拟一下数据:
DROP TABLE IF EXISTS #table;
CREATE TABLE #table (prodID NVARCHAR(6), fieldName NVARCHAR(20), fieldValue NVARCHAR(20));
INSERT INTO #table (prodId, fieldName, fieldValue) VALUES
('ABC123', 'name' , 'widget1'),
('ABC123', 'description' , 'Great widget!'),
('ABC123', 'status' , 'reserved'),
('XYZ999', 'name' , 'widget9'),
('XYZ999', 'description' , 'Lovely widget!'),
('XYZ999', 'status' , 'active');
我在这里使用了一个临时表,因为当涉及到dSQL时,表变量更难处理。
在进行透视之前,我们需要两件事,列中的值列表和SQL本身:
DECLARE @cmd NVARCHAR(MAX), @dpvt NVARCHAR(MAX);
SELECT @dpvt = STRING_AGG(fieldName,',')
FROM (SELECT DISTINCT fieldName FROM #table) a;
SET @cmd = '
SELECT prodID, name AS prodName, '+@dpvt+', CURRENT_TIMESTAMP AS createdDate
FROM #table t
PIVOT (
MAX(fieldValue) FOR fieldName IN ('+@dpvt+')
) p;';
整理好后,我们可以执行sp_executeSQL并执行我们的动态透视:
EXEC sys.sp_executesql @cmd;
prodID prodName name description status createdDate
-------------------------------------------------------------------
ABC123 widget1 widget1 Great widget! reserved 2022-11-01 15:34:36.430
XYZ999 widget9 widget9 Lovely widget! active 2022-11-01 15:34:36.430