识别表空间无效对象需执行指定SQL查询dba_segments与dba_objects连接结果,过滤USERS表空间中状态为INVALID或UNUSABLE的TABLE、INDEX、MATERIALIZED VIEW LOG及LOBSEGMENT对象。

怎么识别表空间里的无效对象
无效对象(INVALID 或 UNUSABLE)不报错、不阻塞查询,但占着空间又不能用。最常见的是索引失效后仍留在段里,或物化视图日志损坏残留。
查之前先确认表空间名,比如 USERS,然后执行:
SELECT s.owner, s.segment_name, s.segment_type, o.status AS object_status
FROM dba_segments s
JOIN dba_objects o ON s.owner = o.owner AND s.segment_name = o.object_name
WHERE s.tablespace_name = 'USERS'
AND o.status IN ('INVALID', 'UNUSABLE')
AND o.object_type IN ('TABLE', 'INDEX', 'MATERIALIZED VIEW LOG', 'LOBSEGMENT');
- 必须加
o.object_type过滤,否则会拉回大量包、类型等系统对象,干扰判断 -
MATERIALIZED VIEW LOG容易被忽略——MOVE 失败时它可能状态已坏但不报错 - 分区索引要单独查
dba_ind_partitions,主索引status = 'VALID'不代表所有子分区都可用
DROP PURGE 和 TRUNCATE 哪个能真正释放空间
DROP TABLE 默认不释放磁盘空间,只进回收站;TRUNCATE TABLE 清空数据但不动高水位线(HWM),后续写入仍从高位开始,空间也不还给 OS。
- 真要腾空间,优先用
DROP TABLE t PURGE—— 段立即物理删除,dba_segments里消失,df -h才会变 - 清空回收站:当前用户用
PURGE RECYCLEBIN,DBA 用PURGE DBA_RECYCLEBIN -
TRUNCATE TABLE t REUSE STORAGE比DELETE快,但仅适合确定不再需要历史数据且不关心 HWM 的场景 - 别对
WRH$_开头的 AWR 表执行TRUNCATE或DROP—— 这些是 Oracle 内部表,要用DBMS_WORKLOAD_REPOSITORY包管理
收缩段空间为什么有时失败
ALTER TABLE t SHRINK SPACE CASCADE 看起来很美,但实际限制很多:表必须启用 ROW MOVEMENT,不能含 LOB 列(除非指定 SHRINK SPACE COMPACT),且所在表空间得是本地管理 + ASSM。
- 先开行移动:
ALTER TABLE t ENABLE ROW MOVEMENT - 再 shrink:
ALTER TABLE t SHRINK SPACE CASCADE - 最后关掉:
ALTER TABLE t DISABLE ROW MOVEMENT - 对 AWR 表(如
WRH$_ACTIVE_SESSION_HISTORY)做 shrink 前,务必确认dbms_workload_repository已停用相关快照清理任务,否则 shrink 可能卡住 -
SHRINK不减少数据文件大小,df -h不变;真要缩文件,得先RESIZE,但前提是文件末尾没活动段——常需先MOVE表到其他表空间腾出尾部空间
SYSAUX 和 SYSTEM 表空间清理要格外小心
这两个表空间里多数对象是 Oracle 自己维护的,比如 AWR、审计、统计信息、调度作业。删错一个,可能导致 AWR 报告失效、自动任务停摆、甚至数据库启动失败。
- 查 SYSAUX 占用大户:
SELECT owner, segment_name, segment_type, ROUND(bytes/1024/1024/1024,2) gb FROM dba_segments WHERE tablespace_name = 'SYSAUX' ORDER BY bytes DESC FETCH FIRST 10 ROWS ONLY;—— 关注WRH$_、WRI$_、SQLTX开头的对象 - 清理 AWR 快照:用
DBMS_WORKLOAD_REPOSITORY.DROP_SNAPSHOT_RANGE,别手删WRH$_表 - SYSTEM 表空间爆满,大概率是审计表
AUD$胀大。确认audit_trail参数为DB后,可TRUNCATE TABLE sys.aud$(11gR2+ 允许),但必须在维护窗口操作,且提前备份 - 任何对 SYSTEM/SYSAUX 的 DDL 操作,建议先在测试库验证,生产环境优先走 Oracle 官方推荐路径(如
DBMS_STATS.PURGE_STATS清理旧统计信息)
PURGE、SHRINK、RESIZE 是三个不同层级的操作,混用或跳步,就容易出现“明明删了几十 GB,df -h 却纹丝不动”的情况。


















