2014-12-02 33 views
0

今天我的问题与标记满足给定条件的连续时间段有关。我感兴趣的原始数据看起来像这样。确定连续的时间段

Salesman ID  Pay Period ID   Total Commissionable Sales (US dollars) 
1     101      525 
1     102      473 
1     103      672 
1     104      766 
2     101      630 
2     101      625 
..... 

我想标记连续的时间段,其中销售员已达到$ 500或更多的销售额。我的理想结果应该是这样的。

[Salesman ID] [Start time]  [End time] [# Periods] [Average Sales] 
     1    101    101   1    525 
     1    103    107   5    621 
     2    101    103   3    635 
     3    104    106   3    538  

我知道如何去做其他事情,但我找不出一个非超级昂贵的方法来确定开始和结束日期。帮帮我!

+0

不幸的是,我认为这是SQL中的难题。您可以使用递归CTE做一个“迭代”解决方案。如果问题是将行分成几组* * 500,那么您可以使用窗口函数。 – 2014-12-02 20:21:33

+0

是啊..我能想到的大多数解决方案需要许多次迭代。可能会生病只是在Excel中复制这个文件,并通过它编写一个迭代宏来强化它 – 2014-12-02 20:40:29

+0

你只关心前500美元或500美元的增量吗?如果第一个,那么有一个解决方案。问题是增加500美元。 – 2014-12-02 21:46:49

回答

0

尝试类似这样的事情。最内层的select语句基本上在原始表中添加一个新列,并带有一个标志,用于确定新组何时开始。在这个声明之外,我们在运行总数中使用这个标志,然后枚举组 - 我们称这个列[组ID]。剩下的就是过滤[Sales] < 500的行,并按[Salesman ID]和[Group ID]分组。

SELECT [Salesman ID], MIN([Pay Period ID]) AS [Start time], 
    MAX([Pay Period ID]) AS [End time], COUNT(*) AS [# of periods], 
    AVG([Sales]) AS [Average Sales] 
FROM (
    SELECT [Salesman ID], [Pay Period ID], [Sales], 
     SUM(NewGroup) OVER (PARTITION BY [Salesman ID] ORDER BY [Pay Period ID] 
          ROWS UNBOUNDED PRECEDING) AS [Group ID] 
    FROM (
     SELECT T1.*, 
      CASE WHEN T1.[Sales] >= 500 AND (Prev.[Sales] < 500 OR Prev.[Sales] IS NULL) 
       THEN 1 ELSE 0 END AS [NewGroup] 
     FROM MyTable T1 
     LEFT JOIN MyTable Prev ON Prev.[Salesman ID] = T1.[Salesman ID] 
           AND Prev.[Pay Period ID] = T1.[Pay Period ID] - 1 
    ) AS InnerQ 
) AS MiddleQ 
WHERE [Sales] >= 500 
GROUP BY [Salesman ID], [Group ID]