我了解 SQL Server 中的 PIVOT 功能,并且在这里阅读了一些其他问题和答案,但我似乎无法掌握它来完成我需要的操作。我正在尝试进行一些计算,结果如下:
TABLE office_settings
column office_id (bigint not null)
column setting_value (NVARCHAR(500) NOT NULL)
office_id setting_value
--------------------------------------------
4 0.2
4 0.2
4 2
4 3
5 0.2
5 0.2
5 2
5 3
Run Code Online (Sandbox Code Playgroud)
我想使用 PIVOT (假设这是适合该工作的工具)将其转换为这个,基本上是“按”office_id 列“分组”,所以:
office_id value_1 value_2 value_3 value_4
------------------------------------------------------
4 0.2 0.2 2 3
5 0.2 0.2 2 3
Run Code Online (Sandbox Code Playgroud)
我还应该提到,在此过程中我需要将setting_value 列值转换为DECIMAL(4,2) - 以防这对完成它所需的T-SQL 有任何影响。
有任何想法吗?
请尝试以下操作:
select office_id,
[1] as value_1, [2] as value_2,
[3] as value_3, [4] as value_4
from
(
select office_id, setting_value,
row_number() over(partition by office_id order by office_id) rnk
from office_settings
) d
pivot
(
max(setting_value)
for rnk in ([1], [2], [3], [4])
) piv;
Run Code Online (Sandbox Code Playgroud)
或者不使用PIVOT
(生成相同的执行计划):
WITH Numbered AS
(
SELECT
OS.office_id,
OS.setting_value,
row_num = ROW_NUMBER() OVER (
-- Note: non-deterministic
PARTITION BY OS.office_id
ORDER BY OS.office_id)
FROM dbo.office_settings AS OS
)
SELECT
N.office_id,
value_1 = MAX(CASE WHEN N.row_num = 1 THEN N.setting_value ELSE NULL END),
value_2 = MAX(CASE WHEN N.row_num = 2 THEN N.setting_value ELSE NULL END),
value_3 = MAX(CASE WHEN N.row_num = 3 THEN N.setting_value ELSE NULL END),
value_4 = MAX(CASE WHEN N.row_num = 4 THEN N.setting_value ELSE NULL END)
FROM Numbered AS N
GROUP BY
N.office_id;
Run Code Online (Sandbox Code Playgroud)
使用动态 sql(当数据透视列的数量在搜索窗口内变化时很有用):
declare @pivcols as varchar(200);
select @pivcols = stuff((select distinct '],[' + cast(row_number()
over(partition by office_id order by office_id) as varchar(10))
from office_settings
for xml path('')), 1, 2, '') + ']';
declare @pivquery varchar(500);
set @pivquery = 'Select office_id, '+
@pivcols +'
from
(select office_id, setting_value,
row_number() over(partition by office_id order by office_id) rnk
from office_settings
) as d
PIVOT
(
max(setting_value)
for rnk in ( '+ @pivcols +' )
) AS pvt ';
EXECUTE(@pivquery);
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
2125 次 |
最近记录: |