我遇到了问题但无法解决。此外,我无法在互联网的任何地方找到答案。
简化我有一个带有coloumns的大表,其中带有ID的产品的值按年存储:
在我的存储过程中,获取信息的属性是:
如果您想获得有关多个产品的信息,可以使用逗号分隔的产品ID列表,如('654654,543543,987987')。
我的TSQL应该是这样的:
select year,
sum(case when id = @id[1] then value),
sum(case when id = @id[2] then value),
[...]
from table myTable
where year = @year
group by year
order by year
我想做的是迭代逗号分隔的id,对于每个id,我想添加一个像这样的新的select attribut(sum(id = @id [x]然后是value的情况)。
你可以帮我解决这个问题吗?有什么建议可以解决吗?!感谢您的帮助!
答案 0 :(得分:1)
PIVOT操作可以简化查询。
但是,无论如何,构建这样的查询的唯一方法似乎是使用动态SQL。
DECLARE
@Ids NVARCHAR(MAX),
@stmt NVARCHAR(MAX)
SET @Ids = '1,2'
-- Transform Ids into the format PIVOT understands - with square brackets.
-- Primitive way, to not overcomplicate sample.
SET @Ids = '[' + REPLACE(@Ids, ',', '], [') + ']'
PRINT @Ids -- [1], [2]
SET @Stmt = '
SELECT *
FROM Products as p
PIVOT
(
SUM(p.Value)
FOR p.Id IN (' + @Ids + ')
) AS t
ORDER BY Year'
EXEC sp_executesql @Stmt
如果您需要更准确的方法将逗号分隔列表拆分为数组(表格),请参阅此article了解详细信息。
此示例可在SQL Fiddle
上找到答案 1 :(得分:0)
在使用存储过程时,可以使用sp_executesql执行dynimically build SQL语句。
所以,你必须像这样迭代CSV:
DECLARE @List NVARCHAR(MAX) = N'1001,dada,1002,1003'
DECLARE @ProductsID TABLE ( [ID] BIGINT )
DECLARE @XML xml = N'<r><![CDATA[' + REPLACE(@List, ',', ']]></r><r><![CDATA[') + ']]></r>'
INSERT INTO @ProductsID ([ID])
SELECT DISTINCT CAST(Tbl.Col.value('.', 'float') AS bigint)
FROM @xml.nodes('//r') Tbl(Col)
WHERE ISNUMERIC(Tbl.Col.value('.', 'varchar(max)')) = 1
SELECT [ID] FROM @ProductsID
然后,使用具有ID的表来动态构建SQL语句并执行它。