Finding customers with identical orders

前端 未结 3 1350
[愿得一人]
[愿得一人] 2021-01-03 11:24

I need to find customers who have made identical orders. (Using T-SQL)

Order

OrderID Customerer  
1   2   
2   5   
3   6            


        
相关标签:
3条回答
  • 2021-01-03 11:40

    This is an extension of Martin's second suggestion. This will show all matching combinations without any repetitions.

    ;With FmtOL(customer, orderid, complete_order) as
    (            
    SELECT  customer, orderid, complete_order
         FROM    Order O
                        cross apply ( SELECT    CAST(Quantity AS VARCHAR(30))
                                                + '~' + Reference + '~~'
                                      FROM      OrderLine OL
                                      WHERE     OL.OrderID = O.OrderID
                                      ORDER BY  Reference ,
                                                Quantity
                                    FOR
                                      XML PATH('')
                                    ) T ( complete_order )
    )
    SELECT  T1.OrderId, 
            T1.Customer,
            STUFF(C1.a, 1, 2, '') as [SameAs]
    FROM    FmtOL T1
    Cross apply ( SELECT '; ' + 'Customer ' + Cast(T2.Customer as varchar(30)) 
                      + '''s order ' + Cast(T2.OrderID as varchar(30))
                     FROM   FmtOL T2
                     WHERE  T1.Customer < T2.Customer
                       AND T1.OrderId < T2.OrderId
                       AND T1.complete_order = T2.complete_order
                     order by ';' + Cast(T2.Customer as varchar(30)) 
                        + '''s order ' + Cast(T2.OrderID as varchar(30))
                        , t2.orderid
                     for xml path('')
                 ) C1 (a)
      where C1.a is not null
    

    Results should look like this:

    OrderId Customer SameAs 
    1       2        Customer 6's order 3 
    4       2        Customer 8's order 7
    
    0 讨论(0)
  • 2021-01-03 11:52

    Here's the most simple approach.

    -- sample table
    create table x
        (
             LineId int identity(1, 1)
            ,InvoiceFk int
            ,ProductFk int
            ,Quantity int
        )
    
    -- sample data
    insert into x 
    (InvoiceFk, ProductFk, Quantity) values
         (11, 1, 1)
        ,(11, 2, 1)
        ,(11, 3, 1)
        ,(12, 1, 2)
        ,(12, 2, 2)
        ,(12, 3, 2)
        ,(13, 1, 3)
        ,(13, 2, 3)
        ,(13, 3, 3)
    
    -- your order, probably from a parameter
    declare @order table
        (
             InvoiceFk int
            ,ProductFk int
            ,Quantity int
        )
    insert into @order
    (InvoiceFk, ProductFk, Quantity) values
         (14, 1, 1) -- duplicate invoice 11
        ,(14, 2, 1)
        ,(14, 3, 1)
    
    -- your order unique checksum
    declare @orderCheck int
    select @orderCheck = checksum_agg(checksum(ProductFk, Quantity))
    from @order
    
    -- test your order in existing data
    declare @match int
    select @match = 
        (
            select TOP 1 InvoiceFk from
            (
                select
                     InvoiceFk
                    ,checksum_agg(Col1) as Col2
                from
                    (
                    select 
                         InvoiceFk
                        ,checksum(productfk, quantity) as Col1
                    from x
                    ) as T1
                group by
                    InvoiceFk
            ) as T2
            where 
                T2.Col2 = @orderCheck
        )
    
    
    -- evaluate if your order is unique or not
    if (@match is not null)
    begin
        print 'Identical to invoice: ' + Str(@match);
    end
    else
    begin
        print 'Order is unique';
    end
    
    -- clean up sample table
    drop table x    
    

    Best of luck!

    0 讨论(0)
  • 2021-01-03 11:53

    Here's one way.

    SELECT  O1.OrderID ,
            O1.Customer ,
            O2.OrderID ,
            O2.Customer
    FROM    [Order] O1
            JOIN [Order] O2 ON O1.OrderID < O2.OrderID
                               AND O1.Customer <> O2.Customer
    WHERE   NOT EXISTS ( SELECT Quantity ,
                                Reference
                         FROM   OrderLine
                         WHERE  O1.OrderID = OrderLine.OrderID
                         EXCEPT
                         SELECT Quantity ,
                                Reference
                         FROM   OrderLine
                         WHERE  O2.OrderID = OrderLine.OrderID )
            AND NOT EXISTS ( SELECT Quantity ,
                                    Reference
                             FROM   OrderLine
                             WHERE  O2.OrderID = OrderLine.OrderID
                             EXCEPT
                             SELECT Quantity ,
                                    Reference
                             FROM   OrderLine
                             WHERE  O1.OrderID = OrderLine.OrderID )
    

    You can also use XML PATH to simulate GROUP_CONCAT then JOIN the two result sets

    DECLARE @T TABLE
        (
          OrderId INT PRIMARY KEY,
          Customer INT ,
          complete_order VARCHAR(MAX)
        )  
    
        INSERT  INTO @T
                SELECT  *
                FROM    [Order] O
                        CROSS APPLY ( SELECT    CAST(Quantity AS VARCHAR(30))
                                                + '~' + Reference + '~~'
                                      FROM      OrderLine OL
                                      WHERE     OL.OrderID = O.OrderID
                                      ORDER BY  Reference ,
                                                Quantity
                                    FOR
                                      XML PATH('')
                                    ) T ( complete_order )
    
    SELECT  T1.OrderId, 
            T1.Customer
    FROM    @T T1
    WHERE   EXISTS ( SELECT *
                     FROM   @T T2
                     WHERE  T1.Customer <> T2.Customer
                            AND T1.OrderId <> T2.OrderId
                            AND T1.complete_order = T2.complete_order )
    
    0 讨论(0)
提交回复
热议问题