2017-09-22 151 views
0

我有保存deleieverddate的表,其中一些交付日期爲空,其中一些不是我想計算交割日期爲空的計數並跳過日期那些在兩者之間錯過的人。Sql計算大於列值的計數

deleievered date 

NULL 
NULL 
NULL 

數量應爲3

NULL 
NULL 
9/22/2017 
NULL 
10/22/2017 
NULL 

計數應該是1 這裏跳過所有以前這裏deievered日期不爲空

我有試過這個,但它太昂貴了。

DECLARE @myTable TABLE 
    (
     MessageId BIGINT , 
     ReceiverID VARCHAR(100) 
    ) 

DECLARE @mySecondTable TABLE 
    (
     MessageId BIGINT , 
     ReceiverID VARCHAR(100), 
     DeliveredDate DATETIME 
    ) 


DECLARE @myLastTable TABLE 
    (
     MessageId BIGINT , 
     ReceiverID VARCHAR(100) 
    ) 





INSERT INTO @myTable 
     (MessageId , 
      ReceiverID 

     ) 
     SELECT MAX(MessageID) , 
       ReceiverID 
     FROM dbo.CM_MessageStatus 
     WHERE ReceiverID IN (SELECT * 
           FROM string_split(@UserID, ',')) 
       AND DeliveredDate IS NOT NULL 
     GROUP BY ReceiverID 






INSERT INTO @mySecondTable 
     (MessageId , 
      ReceiverID, 
      DeliveredDate 

     ) 

SELECT CM_MessageStatus.MessageID, 
     dbo.CM_MessageStatus.ReceiverID, 
     DeliveredDate 
FROM dbo.CM_MessageStatus 
WHERE DeliveredDate IS NULL AND 

     ReceiverID IN (SELECT * 
          FROM string_split(@UserID, ',')) 
--GROUP BY dbo.CM_MessageStatus.ReceiverID,DeliveredDate 




--Now check each userid 
declare @ReceiverID NVARCHAR(MAX) 
while exists (select * from @mySecondTable) 
BEGIN 

      select top 1 @ReceiverID = ReceiverID 
      from @mySecondTable 
      order by ReceiverID ASC 





     IF EXISTS(SELECT * FROM @myTable WHERE [email protected]) 
     BEGIN 
          INSERT INTO @myLastTable 
            (MessageId , 
             ReceiverID 

            ) 


            SELECT MessageID, 
              @ReceiverID 
            FROM @mySecondTable 
            WHERE DeliveredDate IS NULL 
              AND MessageId > (SELECT 
                 MessageId 
                 FROM 
                 @myTable 
                 WHERE 
                 ReceiverID = @ReceiverID 
                ) 
                 AND [email protected] 
                 --GROUP BY ReceiverID 
     END 


     ELSE 
     BEGIN 
       INSERT INTO @myLastTable 
            (MessageId , 
             ReceiverID 

            ) 
            SELECT MessageID , 
              ReceiverID 
            FROM @mySecondTable 
            WHERE DeliveredDate IS NULL 
            AND [email protected] 
     END 


     delete @mySecondTable 
     where ReceiverID = @ReceiverID 
END 

    SELECT COUNT(MessageId) AS MessageId,ReceiverID FROM @myLastTable 
    GROUP BY ReceiverID 

80秒花了35秒,這太昂貴了,我怎麼能在一個選擇中做到這一點。努力是分享這個問題。

+0

您的記錄排序對於此邏輯似乎非常重要。你如何確定訂單? – JNevill

+0

我不要去訂購方向? – bilal

+0

你的數據的排序是什麼?交貨日期是否總是大於上一行?如果沒有,是否有ID列或代表數據序列的東西?像MessageId也許? – scsimon

回答

0

那麼,你必須有一些命令的數據。也就是說,是一個ID列,或者表示插入行的時間與所有其他行相比的時間。在這個例子中,我使用MessageID。每插入一行,它都會得到一個比以前大1的新MessageID。如果沒有SOME列(插入日期)或PrimaryKey/Auto Increment列,這是不可能的。所以,如果你有一個,這裏是你如何做到這一點。

declare @table table (MessageId int identity(1,1), dt date) 
insert into @table 

values 
(NULL), 
(NULL), 
('9/22/2017'), 
(NULL), 
('10/22/2017'), 
(NULL) 



select 
    count(*) 
from 
    @table 
where 
    --limits rows to the last one where data is not null 
    MessageID > (
    select max(MessageID) 
    from @table 
    where dt is not null) 
or 
    --if all dates are null 
    (
    select max(dt) 
    from @table) is null 
+0

您的解決方案無二的最後一排我有我要檢查每一個commaseprated用戶ReceiverID在桌子(SELECT * FROM string_split(@UserID,」, ') DECLARE @UserID NVARCHAR(MAX)=' 123,456,789 ,10' – bilal

+0

那麼,你沒有在原來的帖子中說過,但是你可以在where子句中這麼做......並且如果你需要爲每個用戶統計一下,請將用戶ID添加到select和a按你需要詳細說明。 – scsimon

+0

從 選擇 COUNT(*) dbo.CM_MessageStatus 其中 --limits行的最後一個地方的數據不爲空 MessageStatusID>( 選擇MAX(MessageStatusID) 從dbo.CM_MessageStatus 其中DeliveredDate不是null,ReceiverID IN( '4284924b43ee473580a01eb000f78e82') \t) 或 --IF所有日期從DBO空 ( 選擇MAX(DeliveredDate) 。CM_MessageStatus 其中 \t ReceiverID IN( '4284924b43ee473580a01eb000f78e82') \t \t \t \t \t \t \t \t \t \t \t \t \t \t \t \t \t \t)是NULL – bilal