【问题标题】:Find oldest record by customer?按客户查找最旧的记录?
【发布时间】:2021-07-01 07:29:00
【问题描述】:

对于我的 SQL Server 2016 项目,我有一个 Orders 表,如下所示,我想创建一个 SQL 查询来显示每个客户/产品的最早订单。今天 Orders 表中有数千个订单,我预计它的规模会增长,所以我希望它表现良好。

目标是如下所示的输出:

OrderID CustomerID ProductID OrderDt OrderAmt
123 1 1 1/1/2021 $50
456 1 2 1/2/2021 $20
345 2 1 1/1/2021 $30

今天 Orders 表中的数据如下所示:

OrderID CustomerID ProductID OrderDt OrderAmt
123 1 1 1/1/2021 $50
758 1 1 1/2/2021 $80
563 1 2 1/3/2021 74
684 1 2 1/4/2021 23
456 1 2 1/2/2021 $20
345 2 1 1/1/2021 $30

【问题讨论】:

    标签: sql sql-server


    【解决方案1】:

    规范的方法是使用row_number():

    select t.*
    from (select t.*,
                 row_number() over (partition by customerid, productid order by orderdt, orderid) as seqnum
          from t
         ) t
    where seqnum = 1;
    

    使用(customerid, productid, orderdt) 上的索引,那么相关子查询可能会快一点:

    select t.*
    from t
    where t.orderdt = (select min(t2.orderdt)
                       from t t2
                       where t2.productid = t.productid and t2.customerid = t.customerid
                      );
    

    或者没有子查询的性能稍差的方法:

    select top (1) with ties t.*
    from t
    order by row_number() over (partition by productid, customerid order by orderdt);
    

    【讨论】:

    • 谢谢戈登,我喜欢第二种方法,但我似乎被骗了。应该是orderdt还是orderid?我会认为 min orderdt 但过滤 orderid?
    • 这取决于你如何定义“最古老的”。显然,根据您的评论,您在 orderdt 上有重复项。如果orderididentity 列,那么它的排序应该与orderdt 相同,您可以使用它来代替。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-03-31
    • 2022-01-09
    • 2021-11-22
    • 2018-09-07
    相关资源
    最近更新 更多