[英]How to get cumulative sum of children for all parents in a tree using sql?
所以我有一个 sql 查询来获取无限深度的树结构,如下所示。 但我对获得每个父母的总数一无所知。
我有一个具有 id、dimensionValueId、名称的表 dimensionValue 我有另一个具有 id、dimensionValue 和 volume 的表评估。 需要在每个父级别添加卷。
I have http://sqlfiddle.com/#!15/5c0e7/5
我还想获得累积总数的平坦 sql,目前我只有树。
WITH RECURSIVE hierarchy AS (
SELECT
id,
name,
dimensionvalueid,
0 AS level
FROM
dimensionvalue d
WHERE
dimensionvalueid IS NULL
UNION ALL
SELECT
e.id,
e.name,
e.dimensionvalueid,
hierarchy.level + 1
FROM
dimensionvalue e,
hierarchy
WHERE
e.dimensionvalueid = hierarchy.id
)
SELECT
d.id, d.dimensionvalueid, d.name, v.volume
FROM
hierarchy d
LEFT JOIN valuation v ON v.dimensionvalueid = d.id
GROUP BY
d.id,
d.dimensionvalueid,
d.name,
v.volume
ORDER BY
d.id;
我已经得到了树,但我想获得从下到上到所有父节点的体积累积总和。 在我的应用程序中,仅添加了较低级别的音量,这些音量加到了父级中。
后来我想嵌套平面数据如下:我想要的output是:
[
{
"id": 1,
"name": "A1",
"dimensionValueId": null,
"sumVolume": 300,
"children": [
{
"id": 2,
"name": "A1:1",
"dimensionValueId": 1,
"sumVolume": 300,
"children": [
{
"id": 3,
"name": "A1:1:1",
"dimensionValueId": 2,
"sumVolume": 300,
"children": [
{
"id": 4,
"name": "A1:1:1:1",
"dimensionValueId": 3,
"sumVolume": 200,
"children": null
},
{
"id": 5,
"name": "A1:1:1:2",
"dimensionValueId": 3,
"sumVolume": 100,
"children": null
}
]
}
]
}
]
},
{
"id": 6,
"name": "B1",
"dimensionValueId": null,
"sumVolume": 200,
"children": [
{
"id": 7,
"name": "B1:1",
"dimensionValueId": 6,
"sumVolume": 100,
"children": null
},
{
"id": 8,
"name": "B1:2",
"dimensionValueId": 6,
"sumVolume": 100,
"children": [
{
"id": 9,
"name": "B1:2:1",
"dimensionValueId": 6,
"sumVolume": 100,
"children": null
}
]
}
]
}
]
使用递归cte
:
with recursive cte(id, h) as (
select d.id, ('['||d.id||']')::jsonb from dimensionvalue d where d.dimensionvalueid is null
union all
select d.id, c.h || ('['||c.id||']')::jsonb from cte c
join dimensionvalue d on d.dimensionvalueid = c.id
),
cum_sum(id, s) as (
select d.id, sum(v1.volume) from dimensionvalue d
join cte c on (exists (select 1 from jsonb_array_elements(c.h) v where v.value::int = d.id)
and not exists (select 1 from dimensionvalue d1 where d1.dimensionvalueid = c.id))
join valuation v1 on v1.dimensionvalueid = c.id group by d.id
),
tree(id, p, js) as (
select d.id, d.dimensionvalueid, 'null'::json from dimensionvalue d where not exists (
select 1 from dimensionvalue d1 where d1.dimensionvalueid = d.id)
union all
select d4.id, d4.p, json_agg(d4.js) js from (
select d.id id, d.dimensionvalueid p, json_build_object('id', t.id, 'name', d3.name,
'dimensionValueId', d3.dimensionvalueid,
'sumVolume', coalesce(c.s, v1.volume), 'children', t.js) js
from dimensionvalue d join tree t on d.id = t.p
left join cum_sum c on c.id = t.id join valuation v1 on v1.dimensionvalueid = t.id
join dimensionvalue d3 on d3.id = t.id) d4 group by d4.id, d4.p
)
select jsonb_pretty(t3.js::jsonb) from (
select json_agg(json_build_object('id', t.id, 'name', d3.name, 'dimensionValueId', d3.dimensionvalueid, 'sumVolume', c.s, 'children', t.js)) js
from (select t1.id, json_agg(v.value) js
from tree t1 cross join json_array_elements(t1.js) v
where t1.p is null group by t1.id) t
join cum_sum c on c.id = t.id join dimensionvalue d3 on d3.id = t.id) t3
见小提琴。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.