将数据库结果过滤到查找列中每个值的前n个记录

时间:2011-02-14 05:38:57

标签: sql database ms-access greatest-n-per-group

假设我的数据库中有两个表。

TABLE:Categories
ID|CategoryName
01|CategoryA
02|CategoryB
03|CategoryC

和一个引用类别的表,还有一个存储一些随机数的列。

TABLE:CategoriesAndNumbers
CategoryType|Number
   CategoryA|24
   CategoryA|22
   CategoryC|105
   .....(20,000 records)
   CategoryB|3

现在,如何过滤掉这些数据?所以,我想知道每个类别中3个最小的数字是什么,并删除其余的数字。最终结果是这样的:

TABLE:CategoriesAndNumbers
CategoryType|Number
   CategoryA|2
   CategoryA|5
   CategoryA|18
   CategoryB|3
   CategoryB|500
   CategoryB|1601
   CategoryC|1
   CategoryC|4
   CategoryC|62

现在,我可以获得所有类别之间的最小数字,但我希望每个类别都能单独进行比较。

编辑:我正在使用Access,到目前为止这是我的代码

SELECT TOP 10 cdt1.sourceCounty, cdt1.destCounty, cdt1.distMiles
FROM countyDistanceTable as cdt1, countyTable
WHERE cdt1.sourceCounty = countyTable.countyID
ORDER BY cdt1.sourceCounty, cdt1.distMiles, cdt1.destCounty

EDIT2:感谢Remou,这将是解决我的问题的工作查询。谢谢!

DELETE
FROM CategoriesAndNumbers a
WHERE a.Number NOT IN (
    SELECT Top 3 [Number] 
    FROM CategoriesAndNumbers b 
    WHERE b.CategoryType=a.CategoryType 
    ORDER BY [Number])

2 个答案:

答案 0 :(得分:1)

您可以使用以下内容:

SELECT a.CategoryType, a.Number
FROM CategoriesAndNumbers a
WHERE a.Number IN (
    SELECT Top 3 [Number] 
    FROM CategoriesAndNumbers b 
    WHERE b.CategoryType=a.CategoryType 
    ORDER BY [Number])
ORDER BY a.CategoryType

这方面的困难在于Jet / ACE Top会选择存在的重复值,因此如果存在关联,则不一定会获得三个值,而是更多。如果存在关键字段,通常可以解决问题:

WHERE a.Number IN (
    SELECT Top 3 [Number] 
    FROM CategoriesAndNumbers b 
    WHERE b.CategoryType=a.CategoryType 
    ORDER BY [Number], [KeyField])

但是,我不认为在这种情况下它会有所帮助,因为外表将包含关系。

答案 1 :(得分:0)

按编号排序,取3,找出最大数字,然后删除Number大于Number的行。

我想它需要两个单独的查询,因为您的业务层将保留3个结果中最大数字的值,并动态构建查询以删除其余的。