给出这样的表/数据:
NullPointerException
我需要获取WITH T(col1, col2) AS(
SELECT 1, 'A' FROM DUAL
UNION ALL
SELECT 2, 'B' FROM DUAL
UNION ALL
SELECT 3, 'B' FROM DUAL
UNION ALL
SELECT 4, 'B' FROM DUAL
UNION ALL
SELECT 5, 'A' FROM DUAL
UNION ALL
SELECT 6, 'B' FROM DUAL
UNION ALL
SELECT 7, 'B' FROM DUAL
UNION ALL
SELECT 8, 'A' FROM DUAL
)
队列重复计数,我的意思是,当col2
col2
重复相同值的次数
结果必须是:
col1
我尝试了一些分析功能,但没有达到理想的效果。
可以在" pure"中做到这一点。 SQL?不使用pl / sql(没有循环和每行逐步处理等)
答案 0 :(得分:2)
这是一个差距和岛屿问题。这是解决它的一种方法:
select col1, col2,
count(*) over (partition by col2, seqnum - seqnum_col2) as queue_count
from (select t.*,
row_number() over (partition by col2 order by col1) as seqnum_col2,
row_number() over (order by col1) as seqnum
from t
) t;
有点难以解释为什么会这样。但是,如果您运行子查询并盯着结果,您可能会"得到"为什么行号之间的差异用于识别col2
中具有相同值的相邻行。
答案 1 :(得分:2)
感谢您发布输入数据以便在因子子查询中进行测试,非常感谢!
您没有提及您的Oracle版本(应该包含在每个问题中,因为不同版本允许使用不同的解决方案);无论如何,对于任何使用Oracle 12及更高版本的人来说,使用MATCH_RECOGNIZE都有一个非常简单有效的解决方案。
WITH T ( col1, col2 ) AS (
SELECT 1, 'A' FROM DUAL UNION ALL
SELECT 2, 'B' FROM DUAL UNION ALL
SELECT 3, 'B' FROM DUAL UNION ALL
SELECT 4, 'B' FROM DUAL UNION ALL
SELECT 5, 'A' FROM DUAL UNION ALL
SELECT 6, 'B' FROM DUAL UNION ALL
SELECT 7, 'B' FROM DUAL UNION ALL
SELECT 8, 'A' FROM DUAL
)
select col1, col2, queue_count
from t
match_recognize (
order by col1
measures final count(*) as queue_count
all rows per match
pattern ( A+ | B+ )
define A as A.col2 = 'A',
B as B.col2 = 'B'
)
;
COL1 COL2 QUEUE_COUNT
----- ---- ------------
1 A 1
2 B 3
3 B 3
4 B 3
5 A 1
6 B 2
7 B 2
8 A 1
8 rows selected