2011-03-21 48 views
0

我有一个简单的表,其中包含我希望根据这些值的总和(不超过某个限制组总和)将数据块/分区分成不同组的值。对基于总和的组的SQL查询

例如。想象一个表如下所示:

Key Value 
----------- 
A   1 
B   4 
C   2 
D   2 
E   5 
F   1 

而且我想组进组,使得没有一个分组的总和将超过某一给定值(比如5)。

结果会是这样的:

Group Key Value 
------------------- 
1  A   1  
     B   4 
      -------- 
      Total: 5  

2  C   2 
     D   2 
      -------- 
      Total: 4 

3  E   5 
      -------- 
      Total: 5 

4  F   1 
      -------- 
      Total: 1 

是这样的查询可能吗?

+0

@ user545242 - 这是一个应通过报告引擎解决的问题,或者输出到Excel并启用Excel的小计功能。这不是您应该尝试在数据库中解决的问题类型。 – Thomas 2011-03-21 23:33:06

+0

@Thomas - 我不同意:不熟悉的问题(或问题集)并不意味着SQL引擎不应该这样做。考虑到允许一些约束条件,很有可能存在解决方案等。 – topchef 2011-03-22 01:52:48

+0

@topchef - 我们同意不同意。这个问题完全是关于演示。 SQL语言面向集合的检索。我们可以使用查询来获取总数。我们可以使用查询来获取单个金额的集合。试图让OP在OP中很好地显示,就是报告。即使你可以产生一个返回这些结果的查询,数据层代码也会窒息。正确的答案是提取原始数据并使用报告工具。 – Thomas 2011-03-22 02:48:47

回答

2

虽然我倾向于与评论,这是最好的SQL之外完成的同意,这里是一些SQL这似乎做你的要求大致也是:

with mytable AS (
    select 'A' AS [Key], 1 AS [Value] UNION ALL 
    select 'B', 4 UNION ALL 
    select 'C', 2 UNION ALL 
    select 'D', 2 UNION ALL 
    select 'E', 5 UNION ALL 
    select 'F', 1 
) 
, Sums AS (
    select T1.[Key] AS T1K 
     , T2.[Key] AS T2K 
     , (SELECT SUM([Value]) 
      FROM mytable T3 
      WHERE T3.[Key] <= T2.[Key] 
      AND T3.[Key] >= T1.[Key]) AS TheSum 
    from mytable T1 
    inner join mytable T2 
     on T2.[Key] >= T1.[Key] 
) 
select S1.T1K AS StartKey 
    , S1.T2K AS EndKey 
    , S1.TheSum 
from Sums S1 
left join Sums S2 
    on (S1.T1K >= S2.T1K and S1.T2K <= S2.T2K) 
    and S2.TheSum > S1.TheSum 
    and S2.TheSum <= 5 
where S1.TheSum <= 5 
AND S2.T1K IS NULL 

当我运行这段代码在SQL Server 2008上,我得到以下结果:

StartKey EndKey Sum 
A   B   5 
C   D   4 
E   E   5 
F   F   1 

从这些结果中构建所需的组应该很简单。

+0

谢谢!我会试试看。如果我想在一个组中显示全套密钥(假设我有一个组超过两个),我想我可以尝试一些BETWEEn魔法。 – akowal 2011-03-22 17:01:03

0

如果你想在每一组只有两个成员或更低,则可以使用下面的查询:

Select 
    A.[Key] as K1 , 
    B.[Key] as K2 , 
    isnull(A.value,0) as V1 , 
    isnull(B.value,0) as V2 , 
    (A.value+B.value)as Total 
from Table_1 as A left join Table_1 as B 
on A.value+B.value<=5 and A.[Key]<>B.[Key] 

对于寻找具有更多的成员集,您可以继续使用连接。