索引的并行度解析

一直都对索引的并行度有一些疑惑,今天读到了崔华大神的书中关于index fast full scan的描述,借此机会整理一下。

1.初始化环境

–由于min_servers=0 这时没有px进程存在。

2.创建测试表

保证有足够大的数据量:

3. 下面创建索引

执行期间,我们检查并行进程信息, 可以看到Oracle这时候启用了4个并行进程

此时,上述的并行进程没有被结束,所以Servers Shutdown少了正在执行的4个。

同时可以查看px的session信息,包括各层并行进程的SID和coordinator的SID信息。

检查索引的parallel degree信息:

SH.TEST_IND的并行度设置为创建时指定的4;
由此证明了create index … parallel 4子句不仅在创建index的时候使用了并行(DDL),还会将索引的并行度属性设为4。

4.rebuild索引测试

重建索引是并行DDL操作,会根据PDDL_STATUS的设置有所不同。

4.1 默认情况(PDDL_STATUS=ENABLED)

默认情况下,PDDL_STATUS为TRUE

然后执行rebuild操作

此时我们发现,并没有启用任何并行进程:

而parallel degree也会被置为默认值1:

所以在PDDL_STATUS=ENABLED的情况下,ALTER INDEX REBUILD会改变并行的degree配置。下面使用带着parallel degree子句的REBUILD语句进行测试:

rebuild执行期间,再查询并行会话信息,可以看到成功进行了并行DDL,并行度为2。

而执行之后,并行degree设置为alter index … rebuild语句中指定的2

4.2 PDDL_STATUS=DISABLED

首先,禁用会话的PDDL

下面执行rebuild语句,指定并行度为4:

执行的过程中我们检查V$PX_PROCESS, V$PX_SESSION和PX 统计信息V$PQ_SYSSTAT视图,发现并没有任何并行进程执行,该语句只是将parallel degree设置为了4:

4.3 PDDL_STATUS=FORCE

首先设置会话属性为强制并行DDL:

然后不带parallel子句执行rebuild:

检查V$PX_SESSION和V$PQ_SYSSTAT视图。在不指定parallel子句的情况下,DDL操作如愿的进行了并行:

这里的degree 4是由default值得到,关于default of Parallelism
官方文档 中进行了描述:
For a single instance, DOP = PARALLEL_THREADS_PER_CPU x CPU_COUNT
For an Oracle RAC configuration, DOP = PARALLEL_THREADS_PER_CPU x CPU_COUNT x INSTANCE_COUNT

5. 并行查询

索引的并行查询操作可以通过INDEX FAST FULL SCAN进行实现,下面的描述参考自崔华大神的《基于Oracle的SQL优化》的内容。
INDEX FAST FULL SCAN和INDEX FULL SCAN类似,适用于所有类型的B树索引(包括唯一性索引和非唯一性索引)。和索引全扫描一样,索引快速全扫描也需要扫描目标索引块所有叶子块的所有索引行。进行IFS和IFFS的前提条件之一是目标索引至少有一个索引键值列的属性是NOT NULL。
索引快速全扫描时Oracle是根据索引行在磁盘上的物理存储顺序(如区间内块的相邻)来读取,而不是根据所银行的逻辑顺序(如叶子块之间的相邻)来扫描。所以扫描结果不一定有序。所以Order by 语句时候就不会执行INDEX FAST FULL SCAN。
INDEX FULL SCAN和INDEX FAST FULL SCAN主要有三点区别:
(1). 后者只适用于CBO
(2). 后者可以使用多块读,也可以并行执行。
(3). 索引快速全扫描的执行结果不一定有序。
在实际的执行中,我们可以看到IFFS启动了parallel degree个并行进程进行scan操作:

^^

Posted in Database, Oracle.