从内连接的多行中选择前 1 行

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

我正在尝试准备查询以从联接查询中的多行中查找前 1 行。

我有 2 个表:历史表和新数据表。在新数据表中总是成对出现,但在某些情况下数据不是成对出现的,因此为了找到丢失的对,正在准备查询。

配对表如下

enter image description here

History table as below



Id  Tnum    Snum    Rnum
1   A1234   F1       0
2   A1234   N1       0
3   B1234   SP       2
4   B1234   FW       2
5   A1234   F1       1
6   A1234   N1       1
7   C1234   I1       0
8   C1234   I2       0
9   A1234   F1       2
10  A1234   N1       2


New Data table as below

Id  Tnum    Snum    Rnum
1   A1234   F1       3
2   B1234   FW       3
3   C1234   I2       1

按照配对表,新数据应始终成对意味着如果 Snum 为 F1,则还应有该 Tnum 的 N1 记录,如果 Snum 为 FW,则还应有 SP 记录。在新表中,我们可以看到记录不是成对的,所以我必须找到丢失的对。

我如何检查缺失对:检查历史表中缺失对的先前条目并获取该缺失对的最新 Rnum 条目。例如:在数据表中,Tnum A1234 的 Snum = F1。对于这个 Tnum,N1 不存在,所以我必须从历史表中获取该 Tnum 的 N1 的最高 Rnum 条目。 对于 Snum = F1 和 Tnum A1234,缺少对条目将为 Snum = N1(对于 Tnum A1234 和 Rnum = 2)

Expected Output of missing pair in new data table as below              
                
 History_Id Tnum    Snum    Rnum
  10        A1234    N1      2
  3         B1234    SP      2
  7         C1234    I1      0

我已经准备了如下查询,但它没有给出预期的输出。它只返回 1 条记录,但它应该返回 3 条记录作为预期输出。

WITH previous_latest_missing_pair as (
    select *
    from history_table
    where id in (
        select max(h.id)
        from history_table h 
        join new_data_table n
            on n.Tnum = h.Tnum 
        where h.Snum = case
            when n.Snum = 'SP' then 'FW'
            when n.Snum = 'FW' then 'SP'
            when n.Snum = 'F1' then 'N1'
            when n.Snum = 'N1' then 'F1'
            when n.Snum = 'I1' then 'I2'
            when n.Snum = 'I2' then 'I1'
            end
    )
)
select h.*
from history_table h
join previous_latest_missing_pair p
    on p.Tnum = h.Tnum
    and p.Snum = h.Snum
    and p.Rnum = h.Rnum

enter image description here

sql sql-server sql-server-2008 join
1个回答
0
投票

有这样的事吗?

with Missing2ndParts as (
    select n.*, P.SecondPart as MissingPart 
    from new_data_table n
         inner join
         Pairs P
         on n.snum=P.FirstPart
    where not exists (select *
      from  new_data_table n2
      where n2.tnum=n.tnum
      and n2.snum=P.SecondPart)
)
select * 
   , (select max(h.rnum)
      from history_table h
      where h.tnum=m.tnum
        and h.snum=m.MissingPart) as RNum

from Missing2ndParts m
© www.soinside.com 2019 - 2024. All rights reserved.