2017-09-22 1 views
0

나는 deleieverddate가 저장되는 테이블을 가지고 있습니다. 전달 된 날짜 중 일부는 null이고 그 중 일부는 delievered date가 null 인 수를 계산하고 delieverd date를 건너 뜁니다. 그 사이에 놓친 사람들.Sql이 열 값보다 큰 수를 계산합니다.

deleievered date 

NULL 
NULL 
NULL 

횟수가 3

즉해야

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

카운트 1 여기에 이전의 모든 deievered 날짜가 내가 가진

null가 아닌 건너 뛸 수 있어야 이것을 시도했지만 너무 비싸다.

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 열 또는 데이터 시퀀스를 나타내는 항목이 있습니까? 메시지 아이디와 같을까요? – scsimon

답변

0

음, 데이터를 주문해야합니다. 즉, ID 열 또는 다른 모든 행과 비교하여 행이 삽입 된시기를 나타내는 항목입니다. 이 예제에서는 MessageID를 사용합니다. 행이 삽입 될 때마다 이전 MessageID보다 1 큰 새로운 MessageID를 가져옵니다. 일부 열 (날짜 삽입)이나 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 절에서 그렇게 할 수 있습니다 ..... 그리고 각 사용자에 대한 틱 개수가 필요하면 select에 사용자 ID를 그룹 별. 당신은 정교해야합니다. 데이터가 null는 아니고 마지막에 행을 --limits 곳 – scsimon

+0

이 에서 dbo.CM_MessageStatus 을 수 (*) 을 선택 MessageStatusID> ( 선택 최대 (MessageStatusID) DeliveredDate가 NULL이 dbo.CM_MessageStatus 및 ReceiverID IN ('4284924b43ee473580a01eb000f78e82') \t) 모든 날짜 굳이 이렇게 또는 가 DBO에서 널 (null) ( 선택 최대 (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

관련 문제