求SQL语句 过滤重复记录 只显示一条

2024-12-04 08:43:13
推荐回答(5个)
回答(1):

挺有趣的问题。下面SQL代码经在ACCESS上对原表(biao)记录可能出现的多种情况都测试成功,可以实现你的过滤和排序要求:

SELECT t1.*
FROM (SELECT Max(biao.id) AS id,biao.name,Max(t.zdz) as 最大值
FROM biao INNER JOIN (SELECT biao.name, Max(biao.number) AS ZDZ FROM
biao GROUP BY biao.name)t
ON (biao.name=t.name) and (biao.number=t.ZDZ)
GROUP BY biao.name)t1
ORDER BY t1.id DESC;

代码思路要比上面SQL代码复杂很多,我晚些时候再作补充说明。
现在说明如下:
你的问题的难点在于既要排除重复值又要使用自动ID排序。一般来讲消除重复值使用DISTINCT关键字或分组汇总方法非常方便,但问题是如果输出记录中包含自动ID字段,由于原表中每一条记录的自动ID值都是唯一的,这会导致DISTINCT关键字或分组汇总方法无效,而剔除自动ID字段后虽然可以得到唯一记录,但是唯一记录失去了与自动ID的关联而无法按自动ID字段进行准确排序。
前面的多位网友对你的问题做出了认真的答复,但是解决的不尽完善。为了解决这个矛盾我上面的SQL代码采用了三重嵌套查询加以解决:
第一层(最底层子查询表)对原表(biao)用分组方法获取无name重复值和其number最大值的子查询表并取表别名"t“ (SELECT biao.name, Max(biao.number) AS ZDZ FROM biao GROUP BY biao.name)t ;
第二层 (第二重子查询表取表别名"t1“)用原表与第一层子查询表"t"进行内连接找查出含有自动ID字段和number字段最大值的那些记录,请注意这时查询出来的记录都含有number最大值,但是name字段仍可能含有重复值,怎么办?这里第二次用name字段进行分组并用Max函数找出各组中自动ID字段值最大的那条记录。到此,我们已经过滤字段name重复值并且选取number 最大值并得到与记录准确对应的自动ID值,自动ID降序排序任务交由第三层查询实施(若在此时实施会导致第二层查询失败)
(SELECT Max(biao.id) AS id,biao.name,Max(t.zdz) as 最大值
FROM biao INNER JOIN t
ON (biao.name=t.name) and (biao.number=t.ZDZ)
GROUP BY biao.name)t1;
第三层(最外重子查询)最后对第二层子查询表" ti "用ID字段进行降序排序得到最终结果集。
SELECT t1.* FROM t1 ORDER BY t1.id DESC

说些题外话,为了提高效率建议为原表的name字段添加索引,不过即使如此,你这种过滤排序操作的系统开销其实还是挺大的,如果你的原表中存有大量的数据,例如数万条记录以上情况更是如此。如无必要,不建议用自动ID排序,以便减小数据库系统负荷或将这种过滤排序操作分散到各个终端系统用编程的方式实现上述目的。

对lxf967341答案的评价:
该方法的确非常简洁,但是有一个小小的缺陷,那就是查询得到的maxid与实际id不一定准确匹配,会导致排序有时会有偏差。另外直接用maxid排序数据库jet引擎可能无法识别,应取别名后再排序,例如order by 别名.maxid desc
偏差举例:
id (自动编号) name number
1 张三 1
2 张三 2
3 李四 1
4 李四 2
5 王五 1
6 张三 1

过滤排序后的结果为
id (自动编号) name 最大值
6 张三 2
5 王五 1
4 李四 2

准确的过滤排序结果应该为如下
id (自动编号) name 最大值
5 王五 1
4 李四 2
2 张三 2

这就是我之前没有采用这种简洁方法的原因。当然如果能接受这种小缺陷的话,这仍然不失为一种好的选择。

回答(2):

ACCESS索引也需要手工设置:进入表的设计,常规中有一项是索引
你把ID,NUMA,NUMBER建立INDEX会提高运行速度
SQL语句如下:查了下资料,只有用嵌套SQL了:
select b.* from test b,
(SELECT test.name, Max(test.number) AS mynumber
FROM test
GROUP BY test.name) c
where b.name=c.name and b.number=c.mynumber
ORDER BY b.id DESC;

回答(3):

willyyw 代码确实有问题,“First()” 和 “Max() ”连用,并没有关联起来,导致显示的只是最大的number 和第一个id 。

速度慢的问题跟Access 本身有关,它本来就不适合管理稍大容量的数据。

回答(4):

select max(id)as maxid ,name,max(number) as maxnumber from biao group by name order by maxid desc

回答(5):

select *
from biao b
where not exists(select * from biao where b.name=name and b.numberorder by id desc