HASH分区新增分区对索引状态的影响(一)

2014-11-24 09:24:10 · 作者: · 浏览: 0

一直认为Oracle对于所有分区的操作都是一样的,只有数据的改变才会导致分区状态的失效,没想到HASH分区的实现方式并不相同。

HASH分区表增加新的分区的一点研究:

看一个范围分区SPLIT的例子:

SQL> CREATE TABLE T_PART
2 (ID NUMBER, NAME VARCHAR2(30))
3 PARTITION BY RANGE (ID)
4 (PARTITION P1 VALUES LESS THAN (10),
5 PARTITION PMAX VALUES LESS THAN (MAXVALUE));

Table created.

SQL> INSERT INTO T_PART
2 SELECT ROWNUM, TNAME
3 FROM TAB;

12 rows created.

SQL> CREATE INDEX IND_T_PART_ID ON T_PART(ID) LOCAL;

Index created.tb

SQL> SELECT INDEX_NAME, PARTITION_NAME, STATUS
2 FROM USER_IND_PARTITIONS
3 WHERE INDEX_NAME = 'IND_T_PART_ID';

INDEX_NAME PARTITION_NAME STATUS
------------------------------ ------------------------------ --------
IND_T_PART_ID P1 USABLE
IND_T_PART_ID PMAX USABLE

SQL> SELECT COUNT(*) FROM T_PART PARTITION (PMAX);

COUNT(*)
----------
3

SQL> ALTER TABLE T_PART SPLIT PARTITION PMAX AT (20)
2 INTO (PARTITION P2, PARTITION P3);

Table altered.

SQL> SELECT INDEX_NAME, PARTITION_NAME, STATUS
2 FROM USER_IND_PARTITIONS
3 WHERE INDEX_NAME = 'IND_T_PART_ID';

INDEX_NAME PARTITION_NAME STATUS
------------------------------ ------------------------------ --------
IND_T_PART_ID P2 USABLE
IND_T_PART_ID P3 USABLE
IND_T_PART_ID P1 USABLE

可以看到,对于范围分区而言,即使是SPLIT包含数据的分区,只要没有真正导致数据发生变化,就不会导致索引的失效。这里将PMAX分区SPLIT成P2和P3两个分区,其中PMAX中的所有数据都进入P2分区,而P3分区为空,这种情况下没有数据的改变,因此所有分区索引的状态都不会变为UNUSABLE。

但是HASH分区的ADD PARTITION并没有遵守这个规则,事实上对于每次ADD分区,都会导致一个分区的数据发生分裂,而分裂的结果不管原分区的数据是否发生变化,都会导致原分区索引状态变为UNUSABLE,至于新增分区的索引状态,则取决于是否有数据的改变。

SQL> CREATE TABLE T_HASH
2 (ID NUMBER)
3 PARTITION BY HASH (ID)
4 (PARTITION P1,
5 PARTITION P2,
6 PARTITION P3,
7 PARTITION P4);

Table created.

SQL> CREATE INDEX IND_T_HASH_ID ON T_HASH(ID) LOCAL;

Index created.

SQL> INSERT INTO T_HASH SELECT ROWNUM FROM TAB;

12 rows created.

SQL> COMMIT;

Commit complete.

SQL> SELECT INDEX_NAME, PARTITION_NAME, STATUS
2 FROM USER_IND_PARTITIONS
3 WHERE INDEX_NAME = 'IND_T_HASH_ID';

INDEX_NAME PARTITION_NAME STATUS
------------------------------ ------------------------------ --------
IND_T_HASH_ID P1 USABLE
IND_T_HASH_ID P2 USABLE
IND_T_HASH_ID P3 USABLE
IND_T_HASH_ID P4 USABLE

SQL> SELECT * FROM T_HASH PARTITION (P1);

ID
----------
6
11

SQL> SELECT * FROM T_HASH PARTITION (P2);

ID
----------
9
10
12

SQL> SELECT * FROM T_HASH PARTITION (P3);

ID
----------
2
5
8

SQL> SELECT * FROM T_HASH PARTITION (P4);

ID
----------
1
3
4
7

下面新增一个PARTITION P5:

SQL> ALTER TABLE T_HASH ADD PARTITION P5;

Table altered.

SQL> SELECT * FROM T_HASH PARTITION (P5);

no rows selected

SQL> SELECT INDEX_NAME, PARTITION_NAME, STATUS
2 FROM USER_IND_PARTITIONS
3 WHERE INDEX_NAME = 'IND_T_HASH_ID';

INDEX_NAME PAR