基于同一字段中的 2 个值的条件分组

Conditional grouping based on 2 values in same field

我有如下数据

Number      ActivityID   UnitID          Description                     Date
1231          3456        334      Issue                     2020-12-01 23:02:44
1231          3457        334      Restarted                 2020-12-01 23:45:44
1231          3458        334      closed till 31-12-9999    2020-12-01 23:46:32
1232          4532        445      Issue                     2020-12-01 23:45:44
1232          4533        445      closed till 31-12-9999    2020-12-01 23:67:44

Number 是票号,Activity 是票号中所有活动的唯一 ID,UnitId 是产品的编号,action 是对已完成的解决和日期的描述。

当工单activity重启后关闭到31-12-9999,则说明在App-A中重启了

如果工单之前只是“closed till 31-12-9999”而没有重新启动activity,这意味着它在app-B中重新启动了。

我的预期结果:

month        AppA       AppB
Dec 2020      1          1

我试图通过以下查询获取它们的数量,

select Format(Date, 'MMMM-yyyy') as Month, sum(AppA) as AppA, sum(AppB) as AppB
from (
    select Date, Description,
        case when lower(Description) like '%31-12-9999%' then 1 else 0 end as AppB, 
        case when lower(Description) like '%Restarted%' then 1 else 0 end as AppA
    from  fct.SurveillanceAction
) a
group by Format(Date, 'MMMM-yyyy')

我不知道如何在逻辑上写入 AppA 计数(当工单 activity 重新启动然后关闭直到 31-12-9999 然后 1)

条件是:

  1. App A只有31-12-9999,之前没有“重启”信息。它应该只计算那些没有重新启动但有 31-12-9999 的那些。
  2. AppB 有“31-12-9999”和重新启动消息,只有在两者连续时才应考虑。

谁能帮帮我?

你需要解析函数然后条件group by如下:

select Format(Date, 'MMMM-yyyy') as Month, 
       count(case when AppA> 0 and AppB> 0 then 1 end) as AppA, 
       count(case when AppA> 0 and AppB = 0 then 1 end) as AppB
from (select  Date, Description,
              count(case when lower(Description) like '%31-12-9999%' then 1 end) 
                    over (partition by number) as AppB, 
              count(case when lower(Description) like '%Restarted%' then 1 end) 
                    over (partition by number) as AppA
        from  fct.SurveillanceAction)a
group by Format(Date, 'MMMM-yyyy')

如果 Restartedclosed till 31-12-9999 的顺序很重要,那么您可以使用以下查询:

select Format(Date, 'MMMM-yyyy') as Month, 
       count(case when AppA > AppB then 1 end) as AppA, 
       count(case when AppB is null or AppA < AppB then 1 end) as AppB
from (select  Date, Action,
              max(case when lower(Description) like '%31-12-9999%' then Date end) 
                    over (partition by number) as AppB, 
              max(case when lower(Description) like '%Restarted%' then Date end) 
                    over (partition by number) as AppA
        from  fct.SurveillanceAction)a
group by Format(Date, 'MMMM-yyyy')

--更新

如果您只需要在 Restartedclosed till 31-12-9999 连续时进行计数,则使用以下查询:

select Format(Date, 'MMMM-yyyy') as Month, 
       count(case when lower(Description) like '%31-12-9999%' 
             and cnt = 0 then 1 end) as AppA, 
       count(case when lower(Description) like '%31-12-9999%' 
             and lower(lg_Description) like '%Restarted%' then 1 end) as AppB
from (select  Date, Action,
              lag(Description)  
                over (partition by number order by date) as lg_description,
              count(case when lower(Description) like '%Restarted%' then 1 end)
                over (partition by number order by date) as cnt_restarted
        from  fct.SurveillanceAction)a
group by Format(Date, 'MMMM-yyyy')

假设工单仅关闭并重新启动一次(如示例数据中所示),那么您可以使用两个级别的聚合:

select year(max_date), month(max_date),
       sum(is_restart) as A,
       sum(1 - is_restart) as B
from (select number,
             max(case when lg_description = 'Restarted' then 1 else 0 end) as is_restart,
             max(case when lg_description = 'closed till 31-12-9999' then 1 else 0 end) as is_close,
             max(date) as max_date
      from fct.SurveillanceAction sa
      group by number
     ) n
where is_close = 1
group by year(max_date), month(max_date)
order by year(max_date), month(max_date);

月份与 number 的最大日期相关联,这似乎始终是示例数据的“结束日期”。

(这将年份和月份放入单独的列中;这似乎不是问题的重要部分。)