【问题标题】:COUNT to return NULL as 0 in same table in SAS PROC SQL with GROUP BY使用 GROUP BY 在 SAS PROC SQL 中的同一表中使用 COUNT 返回 NULL 作为 0
【发布时间】:2025-12-26 12:20:08
【问题描述】:

我有一个任务,我有 1 张桌子。交易、交易日期和商店名称都有一个唯一的 ID。 我的任务是统计每家商店在 3 月份进行的交易数量。

这本身很简单:

proc sql;
CREATE TABLE marchtransactions AS SELECT DISTINCT COUNT(tr_id) , store_name
FROM transactions
WHERE MONTH(tr_date)=3
GROUP BY store_name;
quit;

这将导致只有在 3 月份有交易时才存在商店的表。 如果一个商店没有事务,它就是一个 NULL,因此,它根本不会出现在表中。

虽然从技术上讲,这项任务很好,但我真的很想展示我桌子上的每一家商店,即使是那些在 3 月份没有进行交易的商店。 所以我也想看看 0 计数值。

我在网上见过很多不同的场景:IFNULL函数、LEFT JOIN、RIGHT JOIN等,但这只是一张表,在SAS PROC SQL中,没有IFNULL这种东西。

我尝试过使用商店名称制作辅助表并使用 LEFT JOIN 之类的方法,但没有成功。我什至尝试使用 CASE WHEN,但完全没有成功(请记住,我是一个初学者,不过我可能做错了其中一件事情):(

知道如何进行这项工作吗?

【问题讨论】:

  • 如果这只是一张交易表,没有商店表,你怎么知道存在哪些商店?您的表格仅列出在某个时间至少进行过一次交易的商店。
  • @ThorstenKettner 是的,但某些商店可能在其他月份有交易,但在 3 月没有。
  • 最好有一个不同的store_name 来源,因为根据它的名字transactions 表很可能是最大的,所以最好按句点过滤它。如果是某年的三月,不是所有的三月,你可以考虑tr_date between date '2021-03-01' and date '2021-03-31'

标签: sql count null sas left-join


【解决方案1】:

不要将此限制为第 3 个月的行。查看所有行,但只有 count 个月 3。(请删除多余的 DISTINCT。)

SELECT
  store_name,
  COUNT(CASE WHEN MONTH(tr_date) = 3 THEN 1 END) AS in_march
FROM transactions
GROUP BY store_name
ORDER BY store_name;

顺便说一下,这称为条件聚合(在聚合中使用CASE WHENFILTER)。

【讨论】:

    【解决方案2】:

    在 SAS 中,布尔表达式的计算结果为 1 (TRUE) 或 0 (FALSE)。所以要“计算”一个条件发生了多少次,只需 SUM() 条件。

    proc sql;
      CREATE TABLE marchtransactions AS
        SELECT store_name, sum(MONTH(tr_date)=3) as march_count
        FROM transactions
        GROUP BY store_name
      ;
    quit;
    

    如果您必须在其他 SQL 实现中做同样的事情,只需使用 CASE 子句。

    sum(case when (MONTH(tr_date)=3) then 1 else 0 end) as march_count
    

    【讨论】: