我正在撰写一份报告,其中列出了每日运营数据的每周总数。报告顶部将有8周作为列。每行都是一辆车。诸如日期范围之类的变量最终会变得动态,在我开发它的时候,它现在更加硬编码了。 8周可以保持硬编码。
这非常有效:
SELECT vehicle, [2] AS W2, [3] AS W3, [4] AS W4, [5] AS W5, [6] AS W6, [7] AS W7, [8] AS W8, [9] AS W9
FROM
(
SELECT
Vehicle
,datepart(week,recordedoneffective) as WeekNum
,sum(totalweight ) AS TotalWeight
from vw_visit_details v, vw_food_stats f
where v.VisitId = f.VisitId
and recordedoneffective between '2015-01-05' and '2015-03-01'
group by vehicle,datepart(week,recordedoneffective)
) src
PIVOT
(
SUM(TotalWeight)
FOR WeekNum IN ([2],[3],[4],[5],[6],[7],[8],[9])
) pvt
ORDER BY pvt.vehicle
结果:
Vehicle W2 W3 W4 W5 W6 W7 W8 W9
Apples - D44CW 2603 7840 3200 1540 3516 2828 3217 3911
Bananas - 664SEC 4063 5004 5935 8734 8333 8663 4591 7807
Capsicum - YPD094 4699 6191 6423 4560 5742 7004 7204 5347
然而,由于WeekNum根据指定的日期而变化,我想将WeekNum转换为一个等级,该等级始终保持静态。为此,我使用了DENSE_RANK,因此将8周数字(本例中为2-9)的范围转换为数字1-8。
SELECT vehicle, [1] AS W1, [2] AS W2, [3] AS W3, [4] AS W4, [5] AS W5, [6] AS W6, [7] AS W7, [8] AS W8
FROM
(
select
Vehicle
,datepart(week,recordedoneffective) as WeekNum
,dense_rank() OVER ( ORDER BY datepart (week,recordedoneffective) ) AS WeekSeq
,sum(totalweight ) AS TotalWeight
from vw_visit_details v, vw_food_stats f
where v.VisitId = f.VisitId
and recordedoneffective between '2015-01-05' and '2015-03-01'
group by vehicle, datepart(week,recordedoneffective)
) src
PIVOT
(
SUM(TotalWeight)
FOR WeekSeq IN ([1],[2],[3],[4],[5],[6],[7],[8])
) pvt
ORDER BY pvt.vehicle
请注意,列名现在是1-8而不是2-9,并且数据透视列已更改。但是现在其余的设置没有正确旋转。
Vehicle W1 W2 W3 W4 W5 W6 W7 W8
Apples - D44CW 2603 NULL NULL NULL NULL NULL NULL NULL
Apples - D44CW NULL 7840 NULL NULL NULL NULL NULL NULL
Apples - D44CW NULL NULL 3200 NULL NULL NULL NULL NULL
Apples - D44CW NULL NULL NULL 1540 NULL NULL NULL NULL
Apples - D44CW NULL NULL NULL NULL 3516 NULL NULL NULL
Apples - D44CW NULL NULL NULL NULL NULL 2828 NULL NULL
Apples - D44CW NULL NULL NULL NULL NULL NULL 3217 NULL
Apples - D44CW NULL NULL NULL NULL NULL NULL NULL 3911
Bananas - 664SEC 4063 NULL NULL NULL NULL NULL NULL NULL
基本上,枢轴不再旋转。两个查询的内部src
结果集完全相同(除了添加新列之外) - 返回相同数量的结果,没有新的空值等。
我想我可能需要GROUP BY
dense_rank() OVER ( ORDER BY datepart(week,recordedoneffective) )
列,但你不能按此分组。还以为我应该尝试删除现在未使用的datepart(week,recordedoneffective)
计算的col - 事实证明,为了在OVER
子句中使用它仍然是必不可少的。
为什么这个支点不起作用?据推测,我可以使用更具动态性的SQL解决问题,但我认为没有理由说这不起作用。
答案 0 :(得分:2)
您的CTE有四列:Vehicle,WeekNum,WeekSeq和TotalWeight。 PIVOT子句引用了后两个;这意味着数据透视的隐式分组基于前两列。因此,对于Vehicle和WeekNum的每个唯一组合,您将获得一行。这在您的结果集中不明确,因为您没有选择WeekNum。
在您的情况下,答案很简单 - 从CTE中删除WeekNum,因为您实际上并未使用它。
答案 1 :(得分:1)
由于您未使用GROUP BY
输出中的DENSE_RANK()
,因此您需要在WeekNum
之前执行PIVOT
步骤。
;WITH cte AS (SELECT Vehicle
,datepart(week,recordedoneffective) as WeekNum
,sum(totalweight ) AS TotalWeight
FROM vw_visit_details v, vw_food_stats f
WHERE v.VisitId = f.VisitId
and recordedoneffective between '2015-01-05' and '2015-03-01'
GROUP BY vehicle, datepart(week,recordedoneffective)
)
,cte2 AS (SELECT vehicle
,dense_rank() OVER ( ORDER BY WeekNum ) AS WeekSeq
,TotalWeight
FROM cte
)
SELECT vehicle, [1] AS W1, [2] AS W2, [3] AS W3, [4] AS W4, [5] AS W5, [6] AS W6, [7] AS W7, [8] AS W8
FROM cte2
PIVOT (SUM(TotalWeight) FOR WeekSeq IN ([1],[2],[3],[4],[5],[6],[7],[8])) pvt
ORDER BY pvt.vehicle