创建会话 ID 存储桶

问题描述 投票:0回答:1

我正在尝试创建一个 session_id 列,根据是否有 30 分钟的间隙将一堆会话分组到存储桶中...

身份证 Session_TM
001 00:15:12
001 00:17:17
001 01:00:00
001 01:55:00
001 01:58:22
002 02:10:10
002 02:15:12
002 04:15:01

我追求的结果是这样的..

身份证 Session_TM_Min Session_TM_Max 会话_ID
001 00:15:12 00:17:17 1
001 01:00:00 01:00:00 2
001 01:55:00 01:58:00 3
002 02:10:10 02:15:12 1
001 04:15:01 04:15:01 2

我已经在 Partition 上尝试过 Row_Number() 但似乎没有什么可以给我带来正确的结果。

任何支持和想法表示赞赏

sql teradata partitioning
1个回答
0
投票

使用您的示例数据(但将所有时间增加一小时,否则这会导致检查 00:15:12* 之前 30 分钟的内容时出现问题):

create table #sessions
(
    ID varchar(3),
    Session_TM time
)

insert into #sessions values
('001','01:15:12'),
('001','01:17:17'),
('001','02:00:00'),
('001','02:55:00'),
('001','02:58:22'),
('002','03:10:10'),
('002','03:15:12'),
('002','05:15:01')

您可以使用 CTE 来建立组,然后进行一些分组和窗口函数来返回您想要的输出:

with myGroups as
(
    select
        *,
        count(newGroup) over (order by Session_TM rows unbounded preceding) as groupNum
    from
    (
        select
            *,
            case when lag(Session_TM,1,'') over (partition by ID order by Session_TM) < dateadd(minute, -30, Session_TM) then 1 end as newGroup
        from #sessions
    ) s
)
select
    g.ID,
    min(g.Session_TM) as Session_TM_Min,
    max(g.Session_TM) as Session_TM_Max,
    row_number() over (partition by g.ID order by g.groupNum) as Session_ID
from myGroups g
group by g.ID,
         g.groupNum

结果:

身份证 Session_TM_Min Session_TM_Max 会话_ID
1 00:15:12 00:17:17 1
1 00:00:00 00:00:00 2
1 00:55:00 00:58:22 3
2 00:10:10 00:15:12 1
2 00:15:01 00:15:01 2

*如果您需要处理午夜 30 分钟内的时间,那么我建议您需要存储日期时间,而不仅仅是时间值。但如果您确实想在没有日期时间的情况下执行此操作,那么您可以添加到 case 语句中,以将 00:30:00 或更早的任何时间明确标记为“新组”。

© www.soinside.com 2019 - 2024. All rights reserved.