MS Access Top 5查询按月和面积分组的多个条件

时间:2012-06-15 04:06:33

标签: sql ms-access-2007

我想使用前5名来捕捉前5名的许多标准。

数据样式是月份日期,区域1,子区域1,子区域2等,类型,每行的唯一标识符。

我想要做的是每个月,并且区域找到前五种类型。

示例数据:


Date              Division        Sub Division       ID 
31/05/2012        Sales                              001
31/05/2012        Sales           Call Centre        002
31/05/2012        Sales           Call Centre        003
31/05/2012        Sales           Store              004
31/05/2012        Marketing                          005
31/05/2012        Marketing        TV                006
30/04/2012        Sales                              001
30/04/2012        Sales           Call Centre        002
30/04/2012        Sales           Call Centre        003
30/04/2012        Sales           Store              004
30/04/2012        Marketing                          005
30/04/2012        Marketing        TV                006

等等。

我所追求的输出是: 每个月在部门级别(不考虑子部门)排名前5 每个子部门每个月的前5名

示例输出:

Date          Top5Areas     Volume
31/05/2012    Sales         100
31/05/2012    Marketing     90
31/05/2012    HR            50
30/04/2012    Sales         100
30/04/2012    Marketing     90
30/04/2012    HR            50
并且取决于相应区域的子部门的级别:
Date          Top5Areas     Volume
31/05/2012    Call Centre   100
31/05/2012    Store         90
31/05/2012    HR            50 
但每组有5个。

我不应该怎么做,并想知道我是否需要通过一些查询来建立结果,或者是否有更好的方法。

提前致谢并感谢您的建议。

    SELECT [TableA].[DisplayVar] AS DisplayVar, [TableB].[Date] AS MonthDate, TableC.        [Divison] AS Divison, Volume
    FROM (SELECT [TableA].[DisplayVar],
    [TableB].[Date],
    TableC.[Divison],
    Volume
      (  SELECT  COUNT() + 1
      FROM    (   SELECT [TableA].[DisplayVar], [TableB].[Date], TableC.[Divison], COUNT()     AS Volume
         FROM    ([TableA] INNER JOIN [TableB] ON [TableA].[ID] = [TableB].[ID]) LEFT JOIN     TableC ON [TableB].ID = TableC.Descriptor
         GROUP BY [TableA].[DisplayVar], [TableB].[Date], TableC.[Divison]
      ) AS T
      WHERE   T.[TableB].[Date] = Data.[TableB].[Date]
      AND     T.Volume > Data.Volume
    ) AS Rank
    FROM    (   SELECT  [TableA].[DisplayVar], [TableB].[Date], TableC.[Divison], COUNT(*)     AS Volume
      FROM    ([TableA] INNER JOIN [TableB] ON [TableA].[ID] = [TableB].[ID]) LEFT JOIN     TableC ON [TableB].ID = TableC.Descriptor
      WHERE   [TableB].[Date] BETWEEN Date() AND DateADD("m", -12, Date())
GROUP BY[TableA].[DisplayVar], [TableB].[Date], TableC.[Divison] ) AS DATA ) AS Data WHERE (((Data.Rank)<=5)) ORDER BY [TableB].[Date] DESC , Volume DESC;

1 个答案:

答案 0 :(得分:0)

我能想到的唯一方法就是在访问中使用相关子查询来进行每个日期的前n个(我认为你在追求)。我认为最简单的方法类似于在其他DBMS中使用ROW_NUMBER()函数,它为您的orignal聚合查询添加了一个额外的字段,给每个分区/日期一个排名,最外面的where子句将其限制为行,其中等级小于或等于5.

SELECT  Date,
        Division,
        Volume
FROM    (   SELECT  Date,
                    Division,
                    Volume,
                    (   SELECT  COUNT(*) + 1
                        FROM    (   SELECT  Date, Division, COUNT(*) AS Volume
                                    FROM    YourTable
                                    GROUP BY Date, Division
                                ) AS T
                        WHERE   T.Date = Data.Date
                        AND     T.Volume > Data.Volume
                    ) AS Rank
            FROM    (   SELECT  Date, Division, COUNT(*) AS Volume
                        FROM    YourTable
                        WHERE   Date BETWEEN DATE() AND DATEADD("m", -12, DATE())
                        GROUP BY Date, Division
                    ) AS DATA
        ) AS Data
WHERE   Rank <= 5

这种情况下的垮台(或利益取决于你的要求)是它没有处理关系,即如果你有10个具有相同音量的分区,那么所有10个将被返回,而不仅仅是5个。

我不确定这是否正是您所需要的,但希望至少可以让您朝着正确的方向前进。