我有一个包含以下列的表格:
Name, Img1, Img2
数据快照如下所示:
Stack, lemon.jpg, null
Stack, null, orange.jpg
Stack,plum.jpg, null
Stack,grape.jpg, aubergine.jpg
与每个名称关联的图像数量没有限制。
但是,我想返回前十张图片,如下所示:
select name, img1, img2, img3, img4, img5, img6 ... img10
我有一个包含以下列的表格:
Name, Img1, Img2
数据快照如下所示:
Stack, lemon.jpg, null
Stack, null, orange.jpg
Stack,plum.jpg, null
Stack,grape.jpg, aubergine.jpg
与每个名称关联的图像数量没有限制。
但是,我想返回前十张图片,如下所示:
select name, img1, img2, img3, img4, img5, img6 ... img10
由于表中的数据是非规范化的,我建议先对数据进行反透视,然后应用 PIVOT 函数将值转换回您想要的最终结果。
第一步是将img1
和img2
列取消旋转为多行:
select d.name,
c.value,
c.col
+ cast(row_number() over(partition by d.name
order by d.name) as varchar(10)) new_col
from yourtable d
cross apply
(
select 'img', img1 union all
select 'img', img2
) c (col, value);
请参阅演示。unpivot 过程会给你一个结果:
| NAME | VALUE | NEW_COL |
-----------------------------------
| Stack | lemon.jpg | img1 |
| Stack | (null) | img2 |
| Stack | (null) | img3 |
| Stack | orange.jpg | img4 |
| Stack | plum.jpg | img5 |
| Stack | (null) | img6 |
| Stack | grape.jpg | img7 |
| Stack | aubergine.jpg | img8 |
然后,您可以将枢轴函数应用于 中的值new_col
,该值是使用row_number()
按名称分区计算的:
select name, img1, img2, img3, img4, img5,
img6, img7, img8, img9, img10
from
(
select d.name,
c.value,
c.col
+ cast(row_number() over(partition by d.name
order by d.name) as varchar(10)) new_col
from yourtable d
cross apply
(
select 'img', img1 union all
select 'img', img2
) c (col, value)
) src
pivot
(
max(value)
for new_col in (img1, img2, img3, img4, img5,
img6, img7, img8, img9, img10)
) piv;
怎么样,
WITH snapshot(n, name, img1, img2) AS
(
SELECT TOP 5
ROW_NUMBER() OVER(ORDER BY Name) n,
name,
img1,
img2
FROM yourtable
WHERE name = 'Stack'
ORDER BY Name
)
SELECT
row1.Name,
row1.Img1,
row1.Img2,
row2.Img1 Img3,
row2.Img2 Img4,
row3.Img1 Img5,
row3.Img2 Img6,
row4.Img1 Img7,
row4.Img2 Img8,
row5.Img1 Img9,
row5.Img2 Img10
FROM snapshot row1
LEFT JOIN snapshot row2 ON row2.n = 2
LEFT JOIN snapshot row3 ON row3.n = 3
LEFT JOIN snapshot row4 ON row4.n = 4
LEFT JOIN snapshot row5 ON row5.n = 5
WHERE row1.n = 1
这通过定义 CTE 来工作,
SELECT TOP 5
ROW_NUMBER() OVER(ORDER BY Name) n,
name,
img1,
img2
FROM yourtable
WHERE name = 'Stack'
ORDER BY Name
结果可能是
N NAME IMG1 IMG2
1 Stack lemon.jpg (null)
2 Stack (null) orange.jpg
3 Stack plum.jpg (null)
4 Stack grape.jpg aubergine.jpg
然后它选择第一行并为所需的每个后续对执行左自连接。