2014-02-25 63 views
0

夏令時計算。下面我們有一個非常難看的工作模式。SQL非常難看GROUP BY

見過這個 - SQL - Ugly combination of GROUP BY and COALESCE

如果我們可以通過設置變量。這不工作 - 也已經刪除了COUNT(*),說明我們所看到的問題..

Declare @subtractor int; 
    select top 10 case 
        when LOGGED_TIME between 
         case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
           when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
           else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
         end 
         and 
         case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
           when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
           else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
         end 
        then 
        Set @subtractor = 5; 
        else 
        Set @subtractor = 6; 
      end 
    CAST(DATEADD(HH, [email protected],LOGGED_TIME) AS date) AS ForDate 
     , txtW=DATENAME(WEEKDAY, DATEADD(HH, [email protected],LOGGED_TIME)) 
     , intW=DATEPART(WEEKDAY, DATEADD(HH, [email protected],LOGGED_TIME)) 
     , intH=DATEPART(HOUR, DATEADD(HH, [email protected],LOGGED_TIME)) 
from SUPPORT_DATABASE.dbo.LOG (nolock) 

這是行得通的。但是,它是一個非常非常醜陋的GROUP BY ..有沒有辦法清理這個呢?

select top 10 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then CAST(dateadd(hh,-5,LOGGED_TIME) AS date) -- DST 
      else CAST(dateadd(hh,-6,LOGGED_TIME) AS date) -- DST 
     end as ForDate, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATENAME(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATENAME(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end as txtW, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATENAME(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATENAME(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end as intW, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATEPART(HOUR,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATEPART(HOUR,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end as intH 
     , COUNT(*) AS Totals 
FROM   SUPPORT_DATABASE.dbo.LOG WITH (nolock) 
GROUP BY case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then CAST(dateadd(hh,-5,LOGGED_TIME) AS date) -- DST 
      else CAST(dateadd(hh,-6,LOGGED_TIME) AS date) -- DST 
     end, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATENAME(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATENAME(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end 
, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATEPART(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATEPART(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end, 
case 
      when LOGGED_TIME between 
       case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
        else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
       and 
       case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
        when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
        else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
       end 
      then DATEPART(HOUR,dateadd(hh,-5,LOGGED_TIME)) -- DST 
      else DATEPART(HOUR,dateadd(hh,-6,LOGGED_TIME)) -- DST 
     end 
+0

適用於需要重構的代碼 - http://codereview.stackexchange.com/ – EkoostikMartin

回答

2

你可以把它包在一個CTE,所以你可以GROUP BY別名:

;WITH cte AS (select 
       case 
          when LOGGED_TIME between 
           case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
            else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
           and 
           case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
            else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
          then CAST(dateadd(hh,-5,LOGGED_TIME) AS date) -- DST 
          else CAST(dateadd(hh,-6,LOGGED_TIME) AS date) -- DST 
         end as ForDate, 
       case 
          when LOGGED_TIME between 
           case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
            else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
           and 
           case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
            else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
          then DATENAME(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
          else DATENAME(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
         end as txtW, 
       case 
          when LOGGED_TIME between 
           case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
            else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
           and 
           case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
            else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
          then DATENAME(WEEKDAY,dateadd(hh,-5,LOGGED_TIME)) -- DST 
          else DATENAME(WEEKDAY,dateadd(hh,-6,LOGGED_TIME)) -- DST 
         end as intW, 
       case 
          when LOGGED_TIME between 
           case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
            else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
           and 
           case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
            when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
            else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
           end 
          then DATEPART(HOUR,dateadd(hh,-5,LOGGED_TIME)) -- DST 
          else DATEPART(HOUR,dateadd(hh,-6,LOGGED_TIME)) -- DST 
         end as intH 
       FROM   SUPPORT_DATABASE.dbo.LOG WITH (nolock)) 
SELECT *,COUNT(*) CT 
FROM cte 
GROUP BY ForDate, txtW, intW, intH 

這是一個簡單的方法來清理東西一點點,肯定就需要重構爲好。

+0

瞭解重構。但是,我們對於供應商數據庫無能爲力的事實相當受限制。 – Leptonator

1

你可以只創建一個UDF:

CREATE FUNCTION dbo.YourFunctionName (@DateTime DATETIME) 
RETURNS DATE 
AS 
BEGIN 
    RETURN 
    (
     SELECT case 
       when @DateTime between 
        case DATEPART(dw,CAST('03/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime)) 
         when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
         else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime))) 
        end 
        and 
        case DATEPART(dw,CAST('11/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime)) 
         when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
         else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(@DateTime) as varchar(4)) as datetime))) 
        end 
       then CAST(dateadd(hh,-5,@DateTime) AS date) -- DST 
       else CAST(dateadd(hh,-6,@DateTime) AS date) -- DST 
      end 
    ); 
END 

然後將查詢很簡單:

SELECT dbo.YourFunctionName(LOGGED_TIME) AS ForDate, 
     DATENAME(WEEKDAY, dbo.YourFunctionName(LOGGED_TIME)) AS txtW 
.... 
GROUP BY dbo.YourFunctionName(LOGGED_TIME); 

或者,如果你將永遠不會再使用這個功能,不wnat創建它爲此,您可以將邏輯移至APPLY,然後參考您的新列:

SELECT fd.ForDate, 
     DATENAME(WEEKDAY, fd.ForDate) AS txtW 
FROM ... 
     CROSS APPLY 
     (
      SELECT case 
        when LOGGED_TIME between 
         case DATEPART(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
          when 1 then dateadd(hh,-4,CAST('03/08/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))--2am minus 6 hours for conversion from UST going to DST 
          else  dateadd(hh,-4,DATEADD(d,15-datepart(dw,CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('03/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
         end 
         and 
         case DATEPART(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) 
          when 1 then dateadd(hh,-3,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)) --2am minus 5 hours for conversion from UST going from DST 
          else  dateadd(hh,-3,DATEADD(d,8-datepart(dw,CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime)),CAST('11/01/'+CAST (YEAR(LOGGED_TIME) as varchar(4)) as datetime))) 
         end 
        then CAST(dateadd(hh,-5,LOGGED_TIME) AS date) -- DST 
        else CAST(dateadd(hh,-6,LOGGED_TIME) AS date) -- DST 
       end as ForDate 
     ) AS fd 
GROUP BY fd.ForDate; 

或者最後您c應該在外部查詢中使用子查詢和唯一的組。

+0

+1爲'交叉應用'的建議。我更喜歡子查詢/ CTE,因爲它們可以在數據庫之間傳輸。但我發現「交叉應用」非常聰明,可能相當有用。 –