PgSQL监控死元组和自动清理状态的SQL语句执行报错ERROR: division by zero原因分析和解决方法

监控死元组和自动清理状态SQL语句,执行后报错,解决方法:

sql 复制代码
报错SQL:
SELECT schemaname, relname, n_live_tup, n_dead_tup,
    (n_dead_tup * 100.0 / (n_live_tup + n_dead_tup)) AS dead_tup_ratio,
    last_autovacuum, last_autoanalyze
 FROM pg_stat_user_tables
 ORDER BY n_dead_tup DESC
 LIMIT 10;

执行后报错如下:

ERROR: division by zero

怎么修改SQL语句?

这个错误是因为有些表的 n_live_tup 和 n_dead_tup 都是零。可以使用以下几种方法修复:

方法1:使用 NULLIF() 函数(推荐)

sql 复制代码
SELECT schemaname, relname,
       n_live_tup, n_dead_tup,
       (n_dead_tup * 100.0 / NULLIF((n_live_tup + n_dead_tup), 0)) AS dead_tup_ratio,
       last_autovacuum, last_autoanalyze
FROM pg_stat_user_tables
ORDER BY n_dead_tup DESC
LIMIT 10;

方法2:使用 CASE 语句

sql 复制代码
SELECT schemaname, relname,
       n_live_tup, n_dead_tup,
       CASE 
           WHEN (n_live_tup + n_dead_tup) = 0 THEN 0 
           ELSE (n_dead_tup * 100.0 / (n_live_tup + n_dead_tup)) 
       END AS dead_tup_ratio,
       last_autovacuum, last_autoanalyze
FROM pg_stat_user_tables
ORDER BY n_dead_tup DESC
LIMIT 10;

方法3:使用 COALESCE() 提供默认值

sql 复制代码
SELECT schemaname, relname,
       n_live_tup, n_dead_tup,
       COALESCE((n_dead_tup * 100.0 / NULLIF((n_live_tup + n_dead_tup), 0)), 0) AS dead_tup_ratio,
       last_autovacuum, last_autoanalyze
FROM pg_stat_user_tables
ORDER BY n_dead_tup DESC
LIMIT 10;

方法4:过滤掉空表(如果业务需要)

sql 复制代码
SELECT schemaname, relname,
       n_live_tup, n_dead_tup,
       (n_dead_tup * 100.0 / (n_live_tup + n_dead_tup)) AS dead_tup_ratio,
       last_autovacuum, last_autoanalyze
FROM pg_stat_user_tables
WHERE (n_live_tup + n_dead_tup) > 0  -- 只处理有数据的表
ORDER BY n_dead_tup DESC
LIMIT 10;

方法5:更完整的解决方案(包含更多信息)

sql 复制代码
SELECT schemaname, relname,
       n_live_tup AS live_tuples,
       n_dead_tup AS dead_tuples,
       (n_live_tup + n_dead_tup) AS total_tuples,
       CASE 
           WHEN (n_live_tup + n_dead_tup) = 0 THEN 0 
           ELSE ROUND((n_dead_tup * 100.0 / (n_live_tup + n_dead_tup))::numeric, 2) 
       END AS dead_tup_ratio_percent,
       pg_size_pretty(pg_total_relation_size(schemaname || '.' || relname)) AS total_size,
       last_autovacuum,
       last_autoanalyze,
       age(now(), COALESCE(last_autovacuum, '1970-01-01'::timestamp)) AS since_last_autovacuum
FROM pg_stat_user_tables
ORDER BY n_dead_tup DESC
LIMIT 10;

推荐使用的方法1(NULLIF)

这是最简洁和高效的方法,它:

  1. 在除数为零时返回 NULL
  2. 避免了除零错误
  3. 代码简洁易读

执行修改后的查询就不会再出现 "division by zero" 错误了。NULLIF() 函数会在 (n_live_tup + n_dead_tup) 为零时返回 NULL,而任何数除以 NULL 都会返回 NULL,从而避免错误。

相关推荐
古法老登瞎折腾6 小时前
大数据智能运维实战(十一):运维 MCP 的工程化——权限、限流、审计与错误处理
java·大数据·运维·spring ai·mcp
琥珀.7 小时前
mysql中json数组转列表查询
linux·运维·服务器
dawnsky.liu7 小时前
在 RHEL 中使用 goose 实现远程主机管理
linux·运维·ai
znnnk7 小时前
数据库被AI“重写”:2026,从CPU中心走向GPU中心
数据库·人工智能·oracle
微微%8 小时前
mysql的安装和使用
数据库·mysql·mysql8安装
Linux运维技术栈9 小时前
CVE-2026-91403 高危漏洞修复:Rocky Linux 9 多版本 JDK 环境清理实操
java·linux·运维
软件派9 小时前
MiniMax M3.1 Flash 高频业务落地实战指南
大数据·数据库·人工智能
云边云科技_云网融合10 小时前
连锁门店组网怎么做?SD-WAN 多分支组网的架构选型、部署与成本结构
服务器·数据库·php
云上先途110 小时前
企业 AI 服务部署周期多久,会不会影响原有业务运转?
大数据·运维·人工智能
泡海椒10 小时前
# 深度解析JQuick-SQL Join重排序与哈希连接执行机制
数据库·sql·哈希算法