You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PostgreSQL:如何识别表中所有行均为NULL的列

找出数据表中全为NULL的列

你的当前SQL是逐行检查各行的空列并拼接标识,所以会返回不同行的空列组合,这不符合“找出整张表中所有行均为NULL的列”的需求。以下是正确的解决方案:

方法1:手动指定列检查(适合列数少的场景)

通过COUNT(column)判断列是否全空(COUNT会自动忽略NULL值,结果为0则说明列中无有效数据)。

单列出结果

SELECT 'A' AS all_null_column FROM t HAVING COUNT(a) = 0
UNION ALL
SELECT 'B' FROM t HAVING COUNT(b) = 0
UNION ALL
SELECT 'C' FROM t HAVING COUNT(c) = 0
UNION ALL
SELECT 'D' FROM t HAVING COUNT(d) = 0;

针对示例表,该查询会仅返回A。

逗号分隔合并结果

如果希望将所有全空列标识合并为一行:

SELECT
  CONCAT_WS(',',
    CASE WHEN COUNT(a) = 0 THEN 'A' END,
    CASE WHEN COUNT(b) = 0 THEN 'B' END,
    CASE WHEN COUNT(c) = 0 THEN 'C' END,
    CASE WHEN COUNT(d) = 0 THEN 'D' END
  ) AS all_null_columns
FROM t;

方法2:动态生成SQL(适合40+列的大表)

当表列数较多时,手动编写每列的判断逻辑效率极低,可以利用数据库的系统表自动生成查询语句:

MySQL 版本

-- 生成列判断逻辑
SELECT GROUP_CONCAT(
  CONCAT('CASE WHEN COUNT(`', column_name, '`) = 0 THEN ''', UPPER(column_name), ''' END')
  SEPARATOR ', '
) INTO @sql
FROM information_schema.columns
WHERE table_schema = '你的数据库名'
  AND table_name = 't';

-- 拼接完整查询并执行
SET @sql = CONCAT('SELECT CONCAT_WS(\',\', ', @sql, ') AS all_null_columns FROM t');
PREPARE stmt FROM @sql;
EXECUTE stmt;
DEALLOCATE PREPARE stmt;

PostgreSQL 版本

DO $$
DECLARE sql_query text;
BEGIN
  SELECT string_agg(
    format('CASE WHEN COUNT(%I) = 0 THEN ''%s'' END', column_name, upper(column_name)),
    ', '
  ) INTO sql_query
  FROM information_schema.columns
  WHERE table_schema = 'public' -- 替换为你的schema
    AND table_name = 't';

  EXECUTE format('SELECT CONCAT_WS('','', %s) AS all_null_columns FROM t', sql_query);
END $$;

关于磁盘空间的补充

删除全空列是否释放磁盘空间取决于数据库存储引擎:

  • MySQL InnoDB:固定长度字段(如INT)的全空列会占用存储空间,删除后会释放;可变长度字段(如VARCHAR)的全空列仅占用少量元数据空间,释放空间有限。
  • PostgreSQL:全空列几乎不占用数据存储空间,仅在系统表中记录列信息,删除后主要减少元数据开销,对磁盘空间释放影响不大。

无论如何,识别全空列后能有效简化数据筛选、视图创建等后续操作。

内容的提问来源于stack exchange,提问作者Holly

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 16:05:41