示例数据集:
+----------+---------+-----+
| order_id | prod_id | qty |
+----------+---------+-----+
| 1 | 1 | 2 |
| 1 | 1 | 4 |
| 1 | 3 | 1 |
| 2 | 1 | 1 |
| 2 | 2 | 2 |
| 3 | 4 | 1 |
| 3 | 4 | 2 |
| 3 | 2 | 3 |
| 3 | 3 | 5 |
| 4 | 1 | 2 |
| 4 | 2 | 3 |
| 4 | 3 | 3 |
| 4 | 4 | 3 |
| 4 | 6 | 2 |
+----------+---------+-----+
我要做的是构建一个“报告”视图,该视图将根据产品代码聚合某些总计。因此,例如,我想要一个列按产品代码1的顺序排列,另一个列具有产品2和3的总计,一个产品代码4和6。
请注意,产品代码的值来自产品类表,因此我实际上希望获得第1类中的所有产品,即产品1,然后是第2类中的所有产品,这将是产品2和3,然后是第3类中的所有产品,即产品4和6。
+----------+--------+--------+--------+
| order_id | c1_tot | c2_tot | c3_tot |
+----------+--------+--------+--------+
| 1 | 6 | 1 | 0 |
| 2 | 1 | 2 | 0 |
| 3 | 0 | 8 | 3 |
| 4 | 2 | 6 | 5 |
+----------+--------+--------+--------+
我可以使用WHERE子句为一列执行此操作:
SELECT
[order_id],
SUM([qty]) AS [c2]
FROM [orders]
WHERE [prod_id] IN (SELECT [id] FROM [product_class] WHERE [class] = 2)
GROUP BY [order_id]
我提出的另一种方法是存储函数,但这似乎是一种冗长的方式:
SELECT DISTINCT
[order_id],
total_products_by_class([order_id],1) AS [c1_tot],
total_products_by_class([order_id],2) AS [c2_tot],
total_products_by_class([order_id],3) AS [c3_tot]
FROM [orders]
我怀疑理论上可以用分析函数完成某些事情吗?...
有没有办法在没有适合视图的存储函数的情况下执行此操作?
更新:更清楚地了解是否需要从子查询中提取产品的值。
答案 0 :(得分:0)
CASE语句可能是您在简单查询中需要执行的操作。
df['TOTAL']=(df.index.get_level_values('POP')*df['PERCENT']).values
df
Out[874]:
PERCENT TOTAL
DATE POP SEX
2015-01-01 100 MALE 0.51 51.0
FEMALE 0.49 49.0
2016-01-01 120 Male 0.52 62.4
FEMALE 0.48 57.6
答案 1 :(得分:0)
我获取了为orders
表提供的示例数据,并根据问题第2段中的描述创建了product_class
表。
示例数据:
create table #orders
(
order_id int
, prod_id int
, qty int
)
create table #product_class
(
id int
, class int
)
insert into #orders
values (1, 1, 2)
, (1, 1, 4)
, (1, 3, 1)
, (2, 1, 1)
, (2, 2, 2)
, (3, 4, 1)
, (3, 4, 2)
, (3, 2, 3)
, (3, 3, 5)
, (4, 1, 2)
, (4, 2, 3)
, (4, 3, 3)
, (4, 4, 3)
, (4, 6, 2)
insert into #product_class
values (1, 1)
, (2, 2)
, (3, 2)
, (4, 3)
, (6, 3)
<强>答案:强>
从问题中写的第一个查询作为灵感开始,我将对product_class
表的引用更改为inner join
,并将class
添加到group by
。在此之后,所有需要进行的操作都是pivot
,以使class
es跨越列而不是行。
select b.order_id
, isnull(b.[1], 0) as c1_tot
, isnull(b.[2], 0) as c2_tot
, isnull(b.[3], 0) as c3_tot
from (
SELECT o.[order_id]
, pc.class
, SUM(o.[qty]) AS [c2]
FROM [#orders] as o
inner join #product_class as pc on o.prod_id = pc.id
GROUP BY o.[order_id]
, pc.class
) as a
pivot (max(a.c2) for a.class in ([1], [2], [3])) as b
输出完全匹配所需的输出。