【问题标题】:Find the Value Within a Column Which is First Not Found在第一个未找到的列中查找值
【发布时间】:2017-04-27 19:29:32
【问题描述】:

我必须编写一个 SQL,其中我必须编写 SQL 来计算 RunID 第一次没有看到。让我用一个例子来解释一下

例如:

RunID | RunDate    | ErrorID
----- | ---------- | ---------
101   | 04/11/2017 | 1
101   | 04/11/2017 | 2
101   | 04/11/2017 | 3
102   | 04/22/2017 | 2
102   | 04/22/2017 | 3
103   | 04/26/2017 | 1
104   | 04/27/2017 | 3
105   | 04/28/2017 | 4

在上面的例子中,RunID 101 有错误 1,2,3。 RunID 102 有 2,3。在第二次运行期间找不到 ErrorID 1。所以,RunID 到现在才第一次看到这里是 102 但是在 RunID 103 中再次找到了 ErrorID 1,最后在 RunID 104 中找不到 ErrorID 1。查询应该给出第一次找不到的 RunID,如 104。

我尝试过使用一些窗口函数,例如超前和滞后,但没有帮助。

以下是预期结果:

第一次没有出现 ErrorID 的日期:2

RunID | RunDate    | ErrorID
----- | ---------- | ---------
103   | 04/26/2017 | 2

因为在 RunID-102 之后从未见过 ErrorID 2(第一个实例未见过)

第一次没有出现 ErrorID 的日期:1

RunID | RunDate    | ErrorID
----- | ---------- | ---------
104   | 04/27/2017 | 1

在 RunID-104 之后从未见过 ErrorID 1

第一次没有出现 ErrorID 的日期:3

RunID | RunDate    | ErrorID
----- | ---------- | ---------
105   | 04/28/2017 | 3

在 RunID-105 之后从未见过 ErrorID 3

【问题讨论】:

  • 显示预期结果。您的问题不清楚,但预期的结果应该有助于澄清。
  • 已编辑帖子,请立即查看
  • 但是在运行 102 中第一次没有遇到 error_id 1?..
  • RunID 102 只有 ErrorID 2,3...在此运行中找不到其他 ErrorID 1
  • 你到底在用什么数据库?

标签: sql postgresql amazon-redshift


【解决方案1】:
--Get the last runDate when an errorID was seen
with t1 as (select runId,runDate,errorID
            ,first_value(runDate) over(partition by errorID order by runDate desc 
                                       rows between unbounded preceding and unbounded following) as last_seen
            from tablename
           )
--Get the next runDate based on the previous result
,t2 as (select runid,errorID,runDate
        ,(select min(runDate) from t1 t11 where t11.runDate>t1.last_seen) as date_first_not_seen
        from t1
       )
--Join it to the original table to get the runID information from that runDate in the previous result (t2)
select distinct t.runid,t2.errorid,t.rundate
from t2
join tablename t on t.rundate=t2.date_first_not_seen

with t1 as (select runId,runDate,errorID
            ,first_value(runDate) over(partition by errorID order by runDate desc 
                                       rows between unbounded preceding and unbounded following) as last_seen
            from tablename)
select distinct
 t1.errorid
,first_value(t.runDate) over(partition by t1.errorID order by t1.runDate desc rows between unbounded preceding and unbounded following) as rundate
,first_value(t.runID) over(partition by t1.errorID order by t1.runDate desc rows between unbounded preceding and unbounded following) as runid
from t1
join tablename t on t.runDate>t1.last_seen

Sample Demo

【讨论】:

    【解决方案2】:
    so=> with l as (
    with m as (
      select distinct max(runid) over(partition by errorid),errorid
      from so80
    )
    , a as (
      select distinct runid,errorid
      from so80
    )
    select distinct min(a.runid) over (partition by m.errorid),m.errorid
    from m
    join a on m.max < a.runid
    )
    select s.*
    from so80 s
    join l on l.min=s.runid and s.errorid=s.errorid
    
    ;
     runid |   rundate    | errorid
    -------+--------------+---------
       104 |  04/27/2017  |       3
       103 |  04/26/2017  |       1
       105 |  04/28/2017  |       4
    (3 rows)
    

    【讨论】:

    • Vao .. 如果 runID 的顺序与 runDates 的顺序不同,即随着 runDates 的增加而增加,这将无法按预期工作。
    • @vkp 我假设他的 OP 想通过 runid 订购 - 他总是提到第一个 runid 没有遇到 errorid,而不是日期......反正不会改变,因为你已经给出了订购我的日期的答案: )
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-06-27
    • 2015-02-01
    • 2011-01-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多