2

我正在尝试根据帐户 ID 连接两个表中的所有字段。帐户 ID 在表 1 中是唯一的,但在表 2 中重复。在表 2 中,我只想为每个 ID 提取一条记录。

表格1:

ID...Field1....Field2

1......aa.........bb  
2......cc.........dd  
3......ee.........ff  
4......gg.........hh  

表 2:

ID...Field3....Field4......Field5

1.....123........123...........123  
1.....345........546...........453   
2.....123........123...........123  
3.....123........123...........123  
4.....123........123...........722   
4.....123........123...........333  
4.....123........123...........123 

我需要根据三个字段中的值从表 2 中选择要提取的 ID。逻辑是这样工作的。在重复项中,选择field3中值最高的ID记录,如果都相同,则选择field4中值最高的记录,如果仍然相同,则选择field4中值最高的记录字段 5。

所以最终结果看起来像这样:

ID....Field1.....Field2.....Field3.....5ield4.....Field5   
1........aa..........bb............345.......546.........452   
2........cc..........dd............123.......123.........123   
3........ee..........ff............123.......123.........123   
4........gg..........hh............123.......123.........722  

太感谢了!这个让我难倒了一段时间

4

4 回答 4

2

jdevelop 有一个好主意,但它没有考虑到 field3 需要优先于 field4 等的事实。

我不相信访问中有行号,这会大大简化事情。我已经很长时间没有使用访问权限了,因此您可能需要修改以下内容,但它应该可以让您几乎一直到那里。如果这是一次努力,那么您可能可以排序然后添加一个自动编号字段。如果不:

SELECT a.id, d.field3, d.field4, max(d.field5) as m_field5
FROM (((Table1 a
INNER JOIN (
    select id, max(field3) as m3
    from table2
    group by id
    ) b on a.id = b.id                        )
INNER JOIN (
    select id, field3, max(field4) as m4
    from table2
    group by id, field3
    ) c
    on b.id = c.id
    and b.m3 = c.field3                       )
INNER JOIN table2 d
    on c.id = d.id
    and c.field3 = d.field3
    and c.m4 = d.field4                       )
group by a.id, d.field3, d.field4

注意:根据 dbenham 的建议
进行了编辑注 2:编辑为连接添加括号,因为在进行多个连接时访问需要额外的括号

如果一次性努力或者您可以获得行号,您可能会执行以下操作:

select id, field3, field4, field5, rownumber
into #temp_ordered
from table2
order by id, field3, field4, field5

select a.*
from #temp_ordered a
inner join (
    select id, min(rownumber) min_rownumber
    from #temp_ordered 
    group by id
    ) b on a.id = b.id and a.rownumber = b.min_rownumber

最好的,大卫

于 2012-08-11T18:35:55.640 回答
1

我假设您为此使用 MSSQL Server。您需要使用CROSS APPLY才能解决问题。

SELECT a.*, x.*
FROM   tb1 a 
CROSS APPLY 
(
    SELECT   TOP 1 *
    FROM     tb2 b
    WHERE    a.id = b.id
    ORDER BY f3 desc, f4 desc, f5 desc
) x

SQLFiddle 演示

于 2012-08-11T14:30:26.527 回答
1

(此答案是在 OP 将 Access 确定为目标数据库之前开发的)

以下 ANSI 语法很有效,适用于各种数据库,包括:

  • Oracle 11 及更高版本(如果 CTE 移至内联视图,则可追溯到 8i)
  • SqlServer 2005 及更高版本
  • PostgreSQL 8.4 及更高版本

.

with t2 as (
  select id,
         field3,
         field4,
         field5,
         row_number()
           over( partition by id
                 order by field3 desc, field4 desc, field5 desc
               ) as pref
    from table2
)
select t1.id,
       t1.field1,
       t1.field2,
       t2.field3,
       t2.field4,
       t2.field5
  from table1 t1
  join t2
    on t1.id=t2.id
   and t2.pref=1

Oracle 有一种使用 KEEP LAST 的更有效方法,无需任何子查询或 CTE。我相信 SqlServer 2012 可能已经引入了类似的功能,但语法不同,但我并不熟悉。

select id,
       field1,
       field2,
       max(field3) keep (dense_rank last order by field3, field4, field5)
       max(field4) keep (dense_rank last order by field3, field4, field5)
       max(field5) keep (dense_rank last order by field3, field4, field5)
  from table1
  join table2 using(id)
 group by id

这是两个 Oracle 查询的SQL Fiddle

于 2012-08-11T18:15:39.400 回答
0
 SELECT T1.ID,F1,F2,MAX(F3) F3,MAX(F4) F4,MAX(F5) F5
 FROM TBL1 T1,TBL2 T2
 WHERE T1.ID=T2.ID
 GROUP BY T1.ID,F1,F2
 ORDER BY T1.ID;
                  (OR)
 SELECT T1.ID,F1,F2,F3,F4,F5
 FROM TBL1 T1,(SELECT ID,MAX(F3) F3,MAX(F4) F4,MAX(F5) F5 FROM TBL2 GROUP BY ID) T2
 WHERE T1.ID=T2.ID
 ORDER BY T1.ID;

我希望这两种解决方案都能奏效。

于 2012-08-11T19:10:37.320 回答