Database 使用Oracle 12C查找具有匹配项的断开序列

Database 使用Oracle 12C查找具有匹配项的断开序列,database,oracle,Database,Oracle,我想检测每个数字的CDR_ID序列中的间隔,因为我正在使用match_recognize分析函数 代码: 这是我得到的结果: NUMBER CDR_ID STATUS_SEQUENCE 003301011849 536 1 003301011849 537 2 003301011849 538 3 003301011849 539

我想检测每个数字的CDR_ID序列中的间隔,因为我正在使用match_recognize分析函数

代码:

这是我得到的结果:

NUMBER          CDR_ID      STATUS_SEQUENCE                         
003301011849    536         1
003301011849    537         2
003301011849    538         3
003301011849    539         4
003301011849    540         5
003301011849    541         6
003301011849    542         7
003301011849    544         8           <-- !!! 
003301011849    545         9
003301011849    546         10
003301011849    547         11
003301011849    548         12
编号CDR\u ID状态\u序列 003301011849 536 1 003301011849 537 2 003301011849 538 3 003301011849 539 4 003301011849 540 5 003301011849 541 6 003301011849 542 7
003301011849 544 8将一些分析相互叠加

with detect_first_in_seq$ as (
    select X.*,
        case when lnnvl(lag(X.cdr_id) over (partition by num order by cdr_id) = X.cdr_id-1) then X.cdr_id end as is_first_cdr_id_in_seq
    from tmp_cdr_gaps X
),
copy_first_in_seq$ as (
    select X.*,
        last_value(is_first_cdr_id_in_seq ignore nulls) over (partition by num order by cdr_id) as first_cdr_id_in_seq
    from detect_first_in_seq$ X
)
select
    X.*,
    row_number() over (partition by num, first_cdr_id_in_seq order by cdr_id) as status_sequence
from copy_first_in_seq$ X
;
通过您的一个稍微修改的查询和一个额外的分析

select num, cdr_id,
    row_number() over (partition by num, sequence_group order by cdr_id) as status_sequence
from tmp_cdr_gaps
    match_recognize (
        partition by num
        order     by cdr_id
        measures  match_number() sequence_group
        all rows per match
        after match skip past last row
        pattern   (section_start in_seq_value*)
        define    in_seq_value as (cdr_id = prev(cdr_id)+1)
    );
最后,使用
match\u recognize
only

select *
from tmp_cdr_gaps
    match_recognize (
        partition by num
        order by cdr_id
        measures count(1) as status_sequence
        all rows per match
        after match skip past last row
        pattern (sequence_group in_sequence*)
        define in_sequence as (cdr_id = prev(cdr_id)+1)
    );
这似乎是可行的,因为我发现,
match\u recognize()
中的聚合函数具有运行聚合的默认操作方式

也感谢您让我更接近于掌握这一对SQL的精彩补充。:-)

至于你,有人能帮我了解一下匹配的语法有什么问题吗

有很多事情是错误的:

  • 定义为
    cdr\u id=prev(cdr\u id)
    in\u seq\u值没有意义。根据这个定义,您是说您想要识别相同
    cdr\u id
    值的序列,而实际上您想要识别增加1的
    cdr\u id
    值的序列
  • 您的
    match_number()status_sequence
    按顺序为每个找到的模式编号。对于
    cdr\u id=prev(cdr\u id)
    。对于
    cdr\u id=prev(cdr\u id)+1
    ,对于
    cdr\u id
    536
    542
    的行以及
    cdr\u id
    544
    548
    的行,这将是
    1
  • select *
    from tmp_cdr_gaps
        match_recognize (
            partition by num
            order by cdr_id
            measures count(1) as status_sequence
            all rows per match
            after match skip past last row
            pattern (sequence_group in_sequence*)
            define in_sequence as (cdr_id = prev(cdr_id)+1)
        );