【问题标题】:looking for a better way to organize 'where' statements in sql寻找一种更好的方法来组织 sql 中的“where”语句
【发布时间】:2021-09-21 23:55:41
【问题描述】:

我对 SQL 很陌生,我正在解决一个问题以了解它,但我有点卡住了。

任务如下:在 CRM 系统中有两个表,“Contacts”(ContactID、Name、CreateDate)和“ContactActivities”(ContactID、Activity、ActivityDate)。每当在 CRM 中为联系人修改某些内容时,都会将新活动添加到 ContactActivities 表中,其中包含联系人的 ContactID 和描述该活动的字符串 Activity。 创建一个查询,指示每个联系人是否发生了某个活动 (1) 或未发生 (0)。该活动应该在创建联系人后的特定时间段内发生(需要 2 周)。

这是我想出的(通过 SQLFiddle here 检查似乎可行):

  (SELECT SIGN(COUNT(*))
    FROM ContactActivities AS c2 
    WHERE c2.Activity = 'opt-in'
      AND c2.ContactID = c1.ContactID
      AND (SELECT MIN(c2.ActivityDate) - c1.CreationDate) < 14
  ) AS OPT_IN,
  (SELECT SIGN(COUNT(*))
    FROM ContactActivities AS c2 
    WHERE c2.Activity = 'purchase'
      AND c2.ContactID = c1.ContactID
      AND (SELECT MIN(c2.ActivityDate) - c1.CreationDate) < 14
  ) AS PURCHASE,
  (SELECT SIGN(COUNT(*))
    FROM ContactActivities AS c2 
    WHERE c2.Activity = 'deleted'
      AND c2.ContactID = c1.ContactID
      AND (SELECT MIN(c2.ActivityDate) - c1.CreationDate) < 14
  ) AS DELETED
FROM Contacts as c1

现在我想知道(实际上我很确定)这可以通过更好地嵌套 WHERE 语句来完成 - 但我真的不知道如何。

我很高兴有任何帮助!

【问题讨论】:

  • 了解 GROUP BY。
  • 表格的图像没有用处,因为无法复制和粘贴它们以创建测试数据以在重新研究答案时使用。相反,提供创建这些示例表所需的 CREATE TABLE 和 INSERT 语句。您还应该为您正在使用的特定 DBMS 提供一个标签。

标签: sql subquery


【解决方案1】:

像这样,使用连接和聚合:

SELECT c1.ContactID
     , MAX(CASE WHEN c2.Activity = 'opt-in'   THEN 1 ELSE 0 END) AS OPT_IN
     , MAX(CASE WHEN c2.Activity = 'purchase' THEN 1 ELSE 0 END) AS PURCHASE
     , MAX(CASE WHEN c2.Activity = 'deleted'  THEN 1 ELSE 0 END) AS DELETED
  FROM      Contacts          AS c1
  LEFT JOIN ContactActivities AS c2
    ON c2.ContactID = c1.ContactID
   AND c2.ActivityDate - c1.CreationDate < 14
 GROUP BY c1.ContactID
;

Updated fiddle

【讨论】:

    【解决方案2】:

    将通过contactid检查条件case when then else end是否为正sum

    select c.CONTACTID
      , sum(case when ACTIVITY='opt-in'   and datediff(ACTIVITYDATE, CREATIONDATE)<=14 then 1 else 0 end) > 0 as OPT_IN
      , sum(case when ACTIVITY='purchase' and datediff(ACTIVITYDATE, CREATIONDATE)<=14 then 1 else 0 end) > 0 as PURCHASE
      , sum(case when ACTIVITY='deleted'  and datediff(ACTIVITYDATE, CREATIONDATE)<=14 then 1 else 0 end) > 0 as DELETED
    from contacts c
    left join contactActivities a
    on a.CONTACTID = c.CONTACTID
    group by c.CONTACTID
    ;
    

    SQL 小提琴here

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-27
      • 2014-10-21
      • 1970-01-01
      相关资源
      最近更新 更多