首页 > 解决方案 > 如何更好地优化 SQL 查询?

问题描述

我写了请求,但恐怕它可能非常未优化,我会遇到问题。

任务:查找没有债务且最后一次付款超过 2 年的用户。没有任何订单的不必要用户

我们有两张表:

用户 tbl (Id (int), LastName (string))
Order tbl (Id (int), UserId (int), IsPaid (bool), DatePaid (Date, not null))

我写了一个 Sql 请求,但我担心我有 20k 的用户和大量的订单

我找到了所有没有债务的人,最后一次还款是两年。现在我想将它们从一般列表中删除,以便保留需要我的用户。
这似乎是个坏主意

SELECT u."Id"
FROM "User" AS u
LEFT JOIN
   (SELECT *
    FROM "Order"
    WHERE "UserId" IN
       (SELECT "Id"
        FROM "User"
        WHERE "Id" NOT IN
           (SELECT DISTINCT "UserId"
            FROM "Order"
            WHERE "IsPaid" IS FALSE )
       )
    AND "DatePaid" > '2016-10-10'
   ) AS p
   ON p."UserId" = u."Id";

标签: sqlpostgresql

解决方案


我想你只是想要这样的东西:

select o.userid
from orders o
group by o.userid
having sum(case when o.isPaid then 1 else 0 end) = count(*) and -- all are paid
       max(o.paymentdate) < current_date - interval '2 year';

请注意,众所周知,日期函数是特定于数据库的。以上使用 ANSI/ISO 标准语法。

如果您想要有关用户的完整信息,那么您可以使用不同的结构:

select u.*
from users u
where not exists (select 1
                  from orders o
                  where o.userid = u.id and not u.ispaid
                 ) and
      not exists (select 1
                  from orders o
                  where o.userid = u.id and
                        u.paymentdate > current_date - interval '2 year'
                 );

推荐阅读