create table SumTable(ID,S1,S2,S3,Val) as
select 'AA',1,1,1, 10 from dual union all
select 'AA',1,1,2, 20 from dual union all
select 'AA',1,2,2, 40 from dual union all
select 'AA',2,2,1, 80 from dual union all
select 'AA',2,3,1,160 from dual union all
select 'AA',3,9,9,320 from dual union all
select 'AA',4,2,1,640 from dual union all
select 'BB',1,1,1, 1 from dual union all
select 'BB',1,1,2, 3 from dual union all
select 'BB',1,1,3, 9 from dual union all
select 'BB',1,2,1, 27 from dual union all
select 'BB',2,2,1, 10 from dual union all
select 'BB',3,2,1, 20 from dual union all
select 'BB',4,1,1, 30 from dual union all
select 'CC',1,1,1,100 from dual union all
select 'CC',1,1,1,200 from dual union all
select 'CC',1,1,1,400 from dual union all
select 'CC',1,1,2,800 from dual;
--■■■分析関数を使用■■■
select ID,S1,S2,S3,Val,
sum(Val) over(partition by ID order by S1,S2,S3) as SumVal
from SumTable
order by ID,S1,S2,S3,Val;
--■■■相関サブクエリを使用■■■
select ID,S1,S2,S3,Val,
(select sum(b.Val)
from SumTable b
where b.ID = a.ID
and (b.S1 < a.S1
or (b.S1 = a.S1 and b.S2 < a.S2)
or (b.S1 = a.S1 and b.S2 = a.S2 and b.S3 <= a.S3))) as SumVal
from SumTable a
order by ID,S1,S2,S3,Val;
--■■■自己結合を使用■■■
select a.ID,a.S1,a.S2,a.S3,a.Val,sum(b.Val) as SumVal
from SumTable a,SumTable b
where b.ID = a.ID
and (b.S1 < a.S1
or (b.S1 = a.S1 and b.S2 < a.S2)
or (b.S1 = a.S1 and b.S2 = a.S2 and b.S3 <= a.S3))
group by a.ID,a.S1,a.S2,a.S3,a.Val,a.RowID
order by a.ID,a.S1,a.S2,a.S3,a.Val;