Share via

Duration between min and max date

Shambhu Rai 1,411 Reputation points
2022-05-19T12:08:58.697+00:00

Hi Expert,

I wanted to calculate max date for prodstatus =5 - min date for prodstatus=4 and max date for prodstatus =6 - min date for prodstatus=5

Create table
CREATE TABLE [dbo].testdata ON [PRIMARY]
GO

Insert
insert into [dbo].[testdata]

values('Prod1000','873','7','2021-06-16', '11-05-2022', '4'),
('Prod1000','873', '18', '2022-05-12',NULL,'7'),
('Prod1000', '873', '19', '2022-05-12', NULL,'5'),
('Prod10000', '1254','4', '2022-03-28', '2022-03-30', '6'),
('Prod10000', '1254','1', '2022-03-3', NULL, '7'),
('Prod10002', '4427', '5', '2022-03-28', '2022-03-31', '4'),
('Prod10002', '4427', '8', '2022-04-01', NULL, NULL),
('Prod10002', '5603', '8', '2022-04-01', NULL, 2)

expected output:

203627-image.png

Azure SQL Database
SQL Server Analysis Services
SQL Server Analysis Services

A Microsoft online analytical data engine used in decision support and business analytics, providing the analytical data for business reports and client applications such as Power BI, Excel, Reporting Services reports, and other data visualization tools.

Developer technologies | Transact-SQL
Developer technologies | Transact-SQL

A Microsoft extension to the ANSI SQL language that includes procedural programming, local variables, and various support functions.

SQL Server | Other
SQL Server | Other

Additional SQL Server features and topics not covered by specific categories

0 comments No comments

Answer accepted by question author

Eric MILA 86 Reputation points
2022-05-19T20:44:20.797+00:00

Hi ShambhuRai

I hope try to bring an answer with this code. For your information, your screen of expected output hasn't same values as your script to create tables for the test.

select 
    b.min_start_date,
    b.max_start_date,
    DATEDIFF(DAY, max_start_date, min_start_date) as [4-5],
    0 as [5-6]
from
(
    select
        (
            select
                min(testdata.PrdStartDate) as min_start_date
            from
                SKARABEE.dbo.testdata
            where
                testdata.prodstatus = 4
        ) as min_start_date,
        (
            select
                max(testdata.PrdStartDate) as min_start_date
            from
                SKARABEE.dbo.testdata
            where
                testdata.prodstatus = 5
        ) as max_start_date
) as B

union

select 
    b.min_start_date,
    b.max_start_date,
    0 as [4-5],
    DATEDIFF(DAY, max_start_date, min_start_date) as [5-6]
from
(
    select
        (
            select
                min(testdata.PrdStartDate) as min_start_date
            from
                SKARABEE.dbo.testdata
            where
                testdata.prodstatus = 5
        ) as min_start_date,
        (
            select
                max(testdata.PrdStartDate) as min_start_date
            from
                SKARABEE.dbo.testdata
            where
                testdata.prodstatus = 6
        ) as max_start_date
) as B

Best Regards

Was this answer helpful?

1 person found this answer helpful.

12 additional answers

Sort by: Most helpful
  1. Naomi Nosonovsky 8,906 Reputation points
    2022-05-19T23:23:25.347+00:00

    And if you don't care about ProdNumber when statuses change, then it would be (see solution). If you wanted difference between min(StartDate) and max(EndDate) for next status, then do changes accordingly

    DROP TABLE IF EXISTS testdata;
    
    CREATE TABLE [dbo].[testdata](
    [Prodnumber] [nchar](20) NULL,
    [Prodid] [nchar](20) NULL,
    [Prodstatusid] [nchar](20) NULL,
    [PrdStartDate] [date] NULL,
    [PrdEndDate] [date] NULL,
    [prodstatus] [nchar](23) NULL
    ) ON [PRIMARY]
    GO
    
    
    insert into [dbo].[testdata]
    
    values('Prod1000','873','7','2021-06-16', '11-05-2022', '4'),
    ('Prod1000','873', '18', '2022-05-12',NULL,'7'),
    ('Prod1000', '873', '19', '2022-05-12', NULL,'5'),
    ('Prod10000', '1254','4', '2022-03-28', '2022-03-30', '6'),
    ('Prod10000', '1254','1', '2022-03-3', NULL, '7'),
    ('Prod10002', '4427', '5', '2022-03-28', '2022-03-31', '4'),
    ('Prod10002', '4427', '8', '2022-04-01', NULL, NULL),
    ('Prod10002', '5603', '8', '2022-04-01', NULL, 2)
    
    
    ;WITH cte AS (SELECT ProdStatus, MIN(PrdStartDate) AS MinStartDate, 
    MAX(t.PrdStartDate) AS MaxStartDate
    
    FROM dbo.testdata t
    
    GROUP BY ProdStatus), cte2 AS (
    
    SELECT 
    CONCAT(TRIM(ProdStatus), ' to ' + CAST(LEAD(CAST(ProdStatus as INT)) 
    OVER (ORDER BY CAST(ProdStatus as INT)) AS VARCHAR(10))) AS [Status],
    cte.MinStartDate AS MinStartDate, LEAD(MaxStartDate) OVER (
    ORDER BY CAST(ProdStatus as INT)) AS MaxStartDate
    FROM cte)
    
    SELECT *, CASE WHEN cte2.MaxStartDate IS NULL THEN 0 
    ELSE DATEDIFF(DAY, MinStartDate, MaxStartDate) end AS Duration
    FROM cte2 WHERE [cte2].[Status] LIKE '[1-9]%to%[1-9]%'
    

    Was this answer helpful?

    1 person found this answer helpful.
    0 comments No comments

  2. Wilko van de Velde 2,241 Reputation points
    2022-05-19T13:53:21.767+00:00

    Your question is not completly clear. But I quess you want the duration between the max StartDate of the current prodStatus and the min Startdate of the previous prodStatus.

    In that case you case use something like this:
    DROP TABLE IF EXISTS #TEMP_testdata
    DROP TABLE IF EXISTS #TEMP_testdataLag

    --CREATE TEMP TABLE FOR EASE OF USE
    SELECT prodstatus, 
     MAX(PrdStartDate) as MaxDate, 
     Min(PrdStartDate) as MinDate
    INTO #TEMP_testdata
    FROM [dbo].[testdata]
    GROUP BY prodstatus
    
    SELECT prodstatus,
     MaxDate,
     LAG(prodstatus) OVER (ORDER BY prodstatus) as PreviousStatus,
     LAG(MinDate) OVER (ORDER BY prodstatus) as MinDatePreviousStatus,
     DATEDIFF(SECOND, MaxDate, LAG(MinDate) OVER (ORDER BY prodstatus)) as Duration,
     RTRIM(LAG(prodstatus) OVER (ORDER BY prodstatus)) + '-' + prodstatus as ColumnHeader
    INTO #TEMP_testdataLag
    FROM #TEMP_testdata
    
    
    SELECT MinDatePreviousStatus AS [Min Start date],
     MaxDate AS [Max Start date],
     [4-5], 
     [5-6], 
     [6-7]
    FROM (
     SELECT *
     FROM #TEMP_testdataLag
     WHERE PreviousStatus IS NOT NULL
     ) AS SourceTable  
    PIVOT  
    (  
      AVG(Duration)  
      FOR ColumnHeader IN ([4-5], [5-6],[6-7])  
    ) AS PivotTable
    

    For your information, the expected result will not be the same because the insert script doesnt have all the dates

    Was this answer helpful?

    1 person found this answer helpful.

  3. Shambhu Rai 1,411 Reputation points
    2022-05-19T19:31:51.46+00:00

    Suggestion pls

    Was this answer helpful?

    0 comments No comments

  4. Shambhu Rai 1,411 Reputation points
    2022-05-19T14:08:48.91+00:00

    it is giving wrong output and also remaining value should be zero instead of null

    203727-image.png

    also creating view getting error
    Msg 111, Level 15, State 1, Line 18
    'CREATE VIEW' must be the first statement in a query batch.

    Was this answer helpful?

    0 comments No comments

Your answer

Answers can be marked as 'Accepted' by the question author and 'Recommended' by moderators, which helps users know the answer solved the author's problem.