暂无图片
暂无图片
3
暂无图片
暂无图片
暂无图片

Oracle 19c 本地索引分区变为 UNUSABLE 后的空间占用验证

原创 Xiaofei Huangfu 1天前
85

适用范围
适用于Oracle 19c
场景概述
通过测试说明Oracle 19c中分区表的不可用索引和索引分区是否占用空间。

实施步骤
1、登录到PDB hrpdb中
使用业务用户hr用户连接

[oracle@19cdb01 ~]$ sqlplus hr/<password>@hrpdb SQL*Plus: Release 19.0.0.0.0 - Production on Thu Aug 13 04:16:28 2026 Version 19.27.0.0.0 Copyright (c) 1982, 2024, Oracle. All rights reserved. --检查容器名称 HR@hrpdb(HRPDB)> show con_name CON_NAME ------------------------------ HRPDB --确认用户 HR@hrpdb(HRPDB)> show user USER is "HR" HR@hrpdb(HRPDB)>

2、创建一个range分区表

HR@hrpdb(HRPDB)> create table sales1 (sales_amt number ,d_date_id number) partition by range (d_date_id)( partition p_2022 values less than (20220101) tablespace XFTBS, partition p_2023 values less than (20230101) tablespace XFTBS, partition p_max values less than (maxvalue) tablespace XFTBS); 2 3 4 5 6 7 Table created

创建range分区表sales1
3、给分区表创建索引

HR@hrpdb(HRPDB)> create index inx_sales_fk1 on sales1(d_date_id) tablespace INX_XFTBS local; Index created. HR@hrpdb(HRPDB)> create index inx_sales_amt on sales1(sales_amt) tablespace INX_XFTBS local; Index created. HR@hrpdb(HRPDB)>

给分区表创建两个本地索引 inx_sales_fk1 和inx_sales_amt 。
4、为分区表插入测试数据

HR@hrpdb(HRPDB)> INSERT INTO sales1(sales_amt, d_date_id) VALUES (50, 2022); 1 row created. HR@hrpdb(HRPDB)> INSERT INTO sales1(sales_amt, d_date_id) VALUES (100, 2023); 1 row created. HR@hrpdb(HRPDB)> commit; Commit complete. HR@hrpdb(HRPDB)> select count(*) from sales1; COUNT(*) ---------- 2

5、查看分区表信息

HR@hrpdb(HRPDB)> col table_name for a15 HR@hrpdb(HRPDB)> col partitioning_type for a10 HR@hrpdb(HRPDB)> col def_tablespace_name for a15 HR@hrpdb(HRPDB)> select table_name, partitioning_type, def_tablespace_name from user_part_tables where table_name='SALES1'; 2 3 TABLE_NAME PARTITIONI DEF_TABLESPACE_ --------------- ---------- --------------- SALES1 RANGE XFTBS HR@hrpdb(HRPDB)>

6、查表中分区的信息

HR@hrpdb(HRPDB)> col table_name for a15 HR@hrpdb(HRPDB)> col partition_name for a15 HR@hrpdb(HRPDB)> col high_value for 9999 HR@hrpdb(HRPDB)> set long 9999999 HR@hrpdb(HRPDB)> select table_name, partition_name, high_value from user_tab_partitions where table_name = 'SALES1' order by table_name, partition_name; 2 3 4 TABLE_NAME PARTITION_NAME HIGH_VALUE --------------- --------------- -------------------- SALES1 P_2022 20220101 SALES1 P_2023 20230101 SALES1 P_MAX MAXVALUE HR@hrpdb(HRPDB)> HR@hrpdb(HRPDB)> select rpad(segment_name,10),partition_name, blocks, bytes from user_segments where segment_type='INDEX PARTITION'; 2 RPAD(SEGMENT_NAME,10) PARTITION_NAME BLOCKS BYTES ---------------------------------------- --------------- ---------- ---------- INX_SALES_ P_2022 8 65536 INX_SALES_ P_2022 8 65536 HR@hrpdb(HRPDB)> SYS@hrpdb(HRPDB)> select rpad(segment_name,10),partition_name, blocks, bytes from dba_segments where segment_type='INDEX PARTITION' and owner='HR' order by 1,2; 2 RPAD(SEGMENT_NAME,10) PARTITION_NAME BLOCKS BYTES ---------------------------------------- --------------- ---------- ---------- INX_SALES_ P_2022 8 65536 INX_SALES_ P_2022 8 65536 SYS@hrpdb(HRPDB)> HR@hrpdb(HRPDB)> select index_name,partition_name,status from user_ind_partitions where partition_name='P_2022' order by 1,2; 2 INDEX_NAME PARTITION_NAME STATUS -------------------- --------------- -------- INX_SALES_AMT P_2022 USABLE INX_SALES_FK1 P_2022 USABLE HR@hrpdb(HRPDB)> SYS@hrpdb(HRPDB)> select index_name,partition_name,status from dba_ind_partitions where index_owner='HR' and partition_name='P_2022' order by 1,2; 2 INDEX_NAME PARTITION_NAME STATUS -------------------- --------------- -------- INX_SALES_AMT P_2022 USABLE INX_SALES_FK1 P_2022 USABLE SYS@hrpdb(HRPDB)>

7、对分区表SALES1中的P_2022分区进行MOVE

HR@hrpdb(HRPDB)> alter table SALES1 move partition P_2022; Table altered. 检查数据库日志 2026-06-19T05:06:29.934561+08:00 HRPDB(3):Some indexes or index [sub]partitions of table HR.SALES1 have been marked unusable

MOVE执行后分区内数据的物理存储位置(ROWID)发生了改变。Oracle 出于数据一致性考虑,会自动将依赖于这些 ROWID 的本地索引(Local Index)分区标记为 UNUSABLE。
8、再次检查表中分区信息

HR@hrpdb(HRPDB)> select rpad(segment_name,10),partition_name, blocks, bytes from user_segments where segment_type='INDEX PARTITION'; 2 no rows selected HR@hrpdb(HRPDB)> SYS@hrpdb(HRPDB)> select rpad(segment_name,10),partition_name, blocks, bytes from dba_segments where segment_type='INDEX PARTITION' and owner='HR' order by 1,2; 2 no rows selected SYS@hrpdb(HRPDB)> select index_name,partition_name,status from dba_ind_partitions where index_owner='HR' and partition_name='P_2022' order by 1,2; 2 INDEX_NAME PARTITION_NAME STATUS -------------------- --------------- -------- INX_SALES_AMT P_2022 UNUSABLE INX_SALES_FK1 P_2022 UNUSABLE SYS@hrpdb(HRPDB)> HR@hrpdb(HRPDB)> select index_name,partition_name,status from user_ind_partitions where partition_name='P_2022' order by 1,2; 2 INDEX_NAME PARTITION_NAME STATUS -------------------- --------------- -------- INX_SALES_AMT P_2022 UNUSABLE INX_SALES_FK1 P_2022 UNUSABLE HR@hrpdb(HRPDB)>

9、恢复索引状态
在日常运维中,如果需要让这些索引重新生效并重新分配空间,必须对其进行重建(Rebuild)

HR@hrpdb(HRPDB)> ALTER INDEX INX_SALES_AMT REBUILD PARTITION P_2022; Index altered. HR@hrpdb(HRPDB)> ALTER INDEX INX_SALES_FK1 REBUILD PARTITION P_2022; Index altered.

再次查询分区表中分区segment信息,查询结果与 第6步中一致,索引状态是USABLE,segment也分配了值。
10、MOVE分区表时保持索引USABLE状态

--move分区表时使用UPDATE INDEXES HR@hrpdb(HRPDB)> HR@hrpdb(HRPDB)> ALTER TABLE sales1 MOVE PARTITION p_2022 tablespace XFTBS UPDATE INDEXES; Table altered. Table altered. HR@hrpdb(HRPDB)> select rpad(segment_name,10),partition_name, blocks, bytes from user_segments where segment_type='INDEX PARTITION'; 2 RPAD(SEGMENT_NAME,10) PARTITION_NAME BLOCKS BYTES ---------------------------------------- --------------- ---------- ---------- INX_SALES_ P_2022 8 65536 INX_SALES_ P_2022 8 65536 HR@hrpdb(HRPDB)> select index_name,partition_name,status from user_ind_partitions where partition_name='P_2022' order by 1,2; 2 INDEX_NAME PARTITION_NAME STATUS -------------------- --------------- -------- INX_SALES_AMT P_2022 USABLE INX_SALES_FK1 P_2022 USABLE --从12c开始当移动分区时,可以通过 ONLINE 子句指定更新所有索引 HR@hrpdb(HRPDB)> ALTER TABLE sales1 MOVE PARTITION p_2022 ONLINE TABLESPACE XFTBS; Table altered.

【总结】19c中分区表的不可用索引和索引分区不占用空间。对分区表MOVE后将分区表中索引状态标记为 不可用用UNUSABLE 的同时,Oracle 会直接释放这些索引分区原本占用的段(Segment)空间。

-the end-

最后修改时间:2026-08-14 09:49:39
「喜欢这篇文章,您的关注和赞赏是给作者最好的鼓励」
关注作者
【版权声明】本文为墨天轮用户原创内容,转载时必须标注文章的来源(墨天轮),文章链接,文章作者等基本信息,否则作者和墨天轮有权追究责任。如果您发现墨天轮中有涉嫌抄袭或者侵权的内容,欢迎发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论