SQL:另一个日期/时间24小时内的最小日期/时间值

SQL:另一个日期/时间24小时内的最小日期/时间值,sql,oracle,oracle11g,Sql,Oracle,Oracle11g,我正在尝试查找在另一个日期/时间值的24小时内出现的第一个日期/时间值 遭遇表: ENC_ID ADMSN_TIME DISCH_TIME 16755387 03/19/13 11:10:00 03/22/13 12:55:00 问题列表: ENC_ID REVIEWED_TIME USER_ID 16755387 03/19/13 13:02:00 FOOBAR 16755387 03/19/13 13:03:00 FOOB

我正在尝试查找在另一个日期/时间值的24小时内出现的第一个日期/时间值

遭遇表:

ENC_ID    ADMSN_TIME         DISCH_TIME
16755387  03/19/13 11:10:00  03/22/13 12:55:00
问题列表:

ENC_ID      REVIEWED_TIME       USER_ID
16755387    03/19/13 13:02:00   FOOBAR
16755387    03/19/13 13:03:00   FOOBAR
16755387    03/20/13 07:52:00   FOOBAR
16755387    03/22/13 08:35:00   FOOBAR
16755387    03/22/13 08:35:00   FOOBAR
16755387    03/22/13 08:35:00   FOOBAR
期望结果集:

ENC_ID    ADMSN_TIME         ADMSN_REVIEW_TIME  ADMSN_REVIEWER  DISCH_REVIEW_TIME  DISCH_REVIEWER
16755387  03/19/13 11:10:00  03/19/13 13:02:00  FOOBAR          03/22/13 08:35:00  FOOBAR
规则:


  • ABS(revieved_TIME-ADMSN_TIME)我提出了以下内容,它适用于一些测试。使用LEAD分析函数和一个并集

    SELECT enc_id,
           admsn_time,
           CASE
              WHEN TO_CHAR (admsn_time, 'DDMMYYYY') =
                      TO_CHAR (admsn_review_time, 'DDMMYYYY')
              THEN
                 admsn_review_time
              ELSE
                 NULL
           END
              AS admsn_review_time,
           CASE
              WHEN TO_CHAR (admsn_time, 'DDMMYYYY') =
                      TO_CHAR (admsn_review_time, 'DDMMYYYY')
              THEN
                 admsn_user
              ELSE
                 NULL
           END
              AS admsn_review_user,
           disch_time,
           CASE
              WHEN TO_CHAR (disch_time, 'DDMMYYYY') =
                      TO_CHAR (disch_review_time, 'DDMMYYYY')
              THEN
                 disch_review_time
              ELSE
                 NULL
           END
              AS disch_review_time,
           CASE
              WHEN TO_CHAR (disch_time, 'DDMMYYYY') =
                      TO_CHAR (disch_review_time, 'DDMMYYYY')
              THEN
                 disch_user
              ELSE
                 NULL
           END
              AS disch_review_user
      FROM (SELECT enc_id,
                   admsn_time,
                   LEAD (admsn_time, 1)
                      OVER (PARTITION BY enc_id ORDER BY admsn_time)
                      admsn_review_time,
                   LEAD (user_id, 1)
                      OVER (PARTITION BY enc_id ORDER BY admsn_time)
                      admsn_user,
                   disch_time,
                   LEAD (disch_time, 1)
                      OVER (PARTITION BY enc_id ORDER BY disch_time)
                      disch_review_time,
                   LEAD (user_id, 1)
                      OVER (PARTITION BY enc_id ORDER BY disch_time)
                      disch_user,
                   ch
              FROM (SELECT e.enc_id,
                           admsn_time,
                           disch_time,
                           'E' AS ch,
                           NULL AS user_id
                      FROM encounter e
                    UNION
                    SELECT enc_id,
                           reviewed_time,
                           reviewed_time,
                           'P',
                           user_id
                      FROM problem_list pl))
     WHERE ch = 'E';
    

    不确定这是否比您的第二个解决方案总体上更有效,但它避免了
    不同的
    ,并将这两个问题加入到
    问题列表中
    。仍然觉得太复杂了-做一个
    unpivot
    然后再做一个
    pivot
    看起来像是一个黑客-但这部分是为了我自己的娱乐:

    select enc_id, admsn_time, admsn_review_time, admsn_reviewer,
        disch_time, disch_review_time, disch_reviewer
    from (
        select enc_id, admsn_time, disch_time, user_id, reviewed_time, review_type
        from (
            select *
            from (
                select e.enc_id, e.admsn_time, e.disch_time,
                    pl.user_id, pl.reviewed_time,
                    row_number() over (partition by e.enc_id
                        order by abs(pl.reviewed_time - e.admsn_time))
                            as admsn_reviewed_rn,
                    row_number() over (partition by e.enc_id
                        order by abs(pl.reviewed_time - e.disch_time))
                            as disch_reviewed_rn
                from encounter e
                left join problem_list pl on pl.enc_id = e.enc_id
            )
            unpivot (rn for review_type in (admsn_reviewed_rn as 'ADMSN',
                disch_reviewed_rn as 'DISCH'))
        )
        where rn = 1
        and (abs(reviewed_time - admsn_time) <= 1
            or abs(reviewed_time - disch_time) <= 1)
    )
    pivot (min(reviewed_time) as review_time, min(user_id) as reviewer
    for review_type in ('ADMSN' as admsn, 'DISCH' as disch))
    /
    

    你的基本问题是如何在时间T受到约束后找到第一次。从这里开始

    SELECT  E.ENC_ID, 
            E.ADMSN_TIME,
            min(REVIEWED_TIME) as ADMSN_REVIEWED_TIME,
    FROM    ENCOUNTER as E
    JOIN    PROBLEM_LIST as P 
    ON      E.ENC_ID = P.ENC_ID
    AND     ADMSN_TIME < REVIEWED_TIME
    AND     REVIEWED_TIME <= ADMSN_TIME + 1
    GROUP BY E.ENC_ID, E.ADMSN_TIME
    
    选择E.ENC\u ID,
    E.ADMSN_时间,
    最小值(审核时间)作为ADMSN审核时间,
    从邂逅到E
    将问题列表作为P连接
    在E.ENC_ID=P.ENC_ID上
    和ADMSN\u时间<审核时间
    
    当你说你想要最小值时,这表明我应该在你的查询中的某个地方看到一个min()函数。@DanBracuk,在子选择中有一个
    min
    <代码>选择分钟(查看时间).
    select enc_id, admsn_time, admsn_review_time, admsn_reviewer,
        disch_time, disch_review_time, disch_reviewer
    from (
        select enc_id, admsn_time, disch_time, user_id, reviewed_time, review_type
        from (
            select *
            from (
                select e.enc_id, e.admsn_time, e.disch_time,
                    pl.user_id, pl.reviewed_time,
                    row_number() over (partition by e.enc_id
                        order by abs(pl.reviewed_time - e.admsn_time))
                            as admsn_reviewed_rn,
                    row_number() over (partition by e.enc_id
                        order by abs(pl.reviewed_time - e.disch_time))
                            as disch_reviewed_rn
                from encounter e
                left join problem_list pl on pl.enc_id = e.enc_id
            )
            unpivot (rn for review_type in (admsn_reviewed_rn as 'ADMSN',
                disch_reviewed_rn as 'DISCH'))
        )
        where rn = 1
        and (abs(reviewed_time - admsn_time) <= 1
            or abs(reviewed_time - disch_time) <= 1)
    )
    pivot (min(reviewed_time) as review_time, min(user_id) as reviewer
    for review_type in ('ADMSN' as admsn, 'DISCH' as disch))
    /
    
        ENC_ID ADMSN_TIME          ADMSN_REVIEW_TIME   ADMSN_ DISCH_TIME          DISCH_REVIEW_TIME   DISCH_
    ---------- ------------------- ------------------- ------ ------------------- ------------------- ------
      16755387 03/19/0013 11:10:00 03/19/0013 13:02:00 FOOBAR 03/22/0013 12:55:00 03/22/0013 08:35:00 FOOBAR
    
    SELECT  E.ENC_ID, 
            E.ADMSN_TIME,
            min(REVIEWED_TIME) as ADMSN_REVIEWED_TIME,
    FROM    ENCOUNTER as E
    JOIN    PROBLEM_LIST as P 
    ON      E.ENC_ID = P.ENC_ID
    AND     ADMSN_TIME < REVIEWED_TIME
    AND     REVIEWED_TIME <= ADMSN_TIME + 1
    GROUP BY E.ENC_ID, E.ADMSN_TIME