PARALLEL (AUTO) Oracle 提示和 PARALLEL_MIN_TIME_THRESHOLD

问题描述

Oracle 提示 PARALLEL (AUTO) 似乎阻止了并行执行。以下是在 12c 开发服务器上,但我们在 19c 服务器上看到了类似的行为。 PARALLEL 产生并行执行,但 PARALLEL (AUTO) 不会。为什么不呢?

drop table ParallelAuto;

create table ParallelAuto as
  select level id from dual connect by level <= 1
;

select pdml_enabled,pdml_status,pddl_status,pq_status 
  from v$session 
  where sid = (select sid from v$mystat where rownum = 1)
;
+--------------+-------------+-------------+-----------+
| PDML_ENABLED | PDML_STATUS | PDDL_STATUS | PQ_STATUS |
+--------------+-------------+-------------+-----------+
| NO           | DISABLED    | ENABLED     | ENABLED   |
+--------------+-------------+-------------+-----------+
alter session ENABLE PARALLEL DML; 

select pdml_enabled,pq_status 
  from v$session 
  where sid = (select sid from v$mystat where rownum = 1)
;
+--------------+-------------+-------------+-----------+
| PDML_ENABLED | PDML_STATUS | PDDL_STATUS | PQ_STATUS |
+--------------+-------------+-------------+-----------+ 
| YES          | ENABLED     | ENABLED     | ENABLED   |
+--------------+-------------+-------------+-----------+

PDML 已启用。

以下是%parallel%参数供参考。

select name,value,isdefault,ismodified,isadjusted 
  from v$parameter 
  where name like '%parallel%'  
;
+---------------------------------+--------+-----------+------------+------------+
| NAME                            | VALUE  | ISDEFAULT | ISMODIFIED | ISADJUSTED |
+---------------------------------+--------+-----------+------------+------------+
| parallel_server                 | FALSE  | TRUE      | FALSE      | FALSE      |
| parallel_server_instances       | 1      | TRUE      | FALSE      | FALSE      |
| recovery_parallelism            | 0      | TRUE      | FALSE      | FALSE      |
| fast_start_parallel_rollback    | LOW    | TRUE      | FALSE      | FALSE      |
| parallel_min_percent            | 0      | TRUE      | FALSE      | FALSE      |
| parallel_min_servers            | 32     | TRUE      | FALSE      | FALSE      |
| parallel_max_servers            | 320    | TRUE      | FALSE      | FALSE      |
| parallel_instance_group         |        | TRUE      | FALSE      | FALSE      |
| parallel_execution_message_size | 16384  | TRUE      | FALSE      | FALSE      |
| parallel_degree_policy          | MANUAL | TRUE      | FALSE      | FALSE      |
| parallel_adaptive_multi_user    | TRUE   | TRUE      | FALSE      | FALSE      |
| parallel_threads_per_cpu        | 2      | TRUE      | FALSE      | FALSE      |
| parallel_automatic_tuning       | FALSE  | TRUE      | FALSE      | FALSE      |
| parallel_io_cap_enabled         | FALSE  | TRUE      | FALSE      | FALSE      |
| parallel_min_time_threshold     | AUTO   | TRUE      | FALSE      | FALSE      |
| parallel_degree_limit           | CPU    | TRUE      | FALSE      | FALSE      |
| parallel_force_local            | FALSE  | TRUE      | FALSE      | FALSE      |
| parallel_servers_target         | 128    | TRUE      | FALSE      | FALSE      |
| parallel_degree_level           | 100    | TRUE      | FALSE      | FALSE      |
+---------------------------------+--------+-----------+------------+------------+

解释这个 UPDATE DML 表明我们确实得到了并行执行。

update /*+ ENABLE_PARALLEL_DML PARALLEL */ ParallelAuto set id = 2;

-------------------------------------------------------------------------------------------------------------------
| Id  | Operation             | Name         | Rows  | Bytes | Cost (%CPU)| Time     |    TQ  |IN-OUT| PQ Distrib |
-------------------------------------------------------------------------------------------------------------------
|   0 | UPDATE STATEMENT      |              |     1 |    13 |     3   (0)| 00:00:01 |        |      |            |
|   1 |  PX COORDINATOR       |              |       |       |            |          |        |      |            |
|   2 |   PX SEND QC (RANDOM) | :TQ10000     |     1 |    13 |     3   (0)| 00:00:01 |  Q1,00 | P->S | QC (RAND)  |
|   3 |    UPDATE             | PARALLELAUTO |       |       |            |          |  Q1,00 | PCWP |            |
|   4 |     PX BLOCK ITERATOR |              |     1 |    13 |     3   (0)| 00:00:01 |  Q1,00 | PCWC |            |
|   5 |      TABLE ACCESS FULL| PARALLELAUTO |     1 |    13 |     3   (0)| 00:00:01 |  Q1,00 | PCWP |            |
-------------------------------------------------------------------------------------------------------------------
...
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 2

但是,当使用 PARALLEL (AUTO) 提示时,我们不再接收并行执行。

update /*+ ENABLE_PARALLEL_DML PARALLEL (AUTO) */ ParallelAuto set id = 3;

-----------------------------------------------------------------------------------
| Id  | Operation          | Name         | Rows  | Bytes | Cost (%CPU)| Time     |
-----------------------------------------------------------------------------------
|   0 | UPDATE STATEMENT   |              |     1 |    13 |     5   (0)| 00:00:01 |
|   1 |  UPDATE            | PARALLELAUTO |       |       |            |          |
|   2 |   TABLE ACCESS FULL| PARALLELAUTO |     1 |    13 |     5   (0)| 00:00:01 |
-----------------------------------------------------------------------------------
...
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 1 because of parallel threshold
   - PDML disabled because object is not decorated with parallel clause

只是为了确认它不是 PARALLEL_DEGREE_POLICY,让我们将其更改为不是 MANUAL

alter session set parallel_degree_policy = AUTO;

select name,isadjusted
  from v$parameter
  where name like 'parallel_degree_policy'
;
+---------------------------------+--------+-----------+------------+------------+
| NAME                            | VALUE  | ISDEFAULT | ISMODIFIED | ISADJUSTED |
+---------------------------------+--------+-----------+------------+------------+
| parallel_degree_policy          | AUTO   | TRUE      | MODIFIED   | FALSE      |
+---------------------------------+--------+-----------+------------+------------+
update /*+ ENABLE_PARALLEL_DML PARALLEL */ ParallelAuto set id = 3;
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 2
update /*+ ENABLE_PARALLEL_DML PARALLEL (AUTO) */ ParallelAuto set id = 3;
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 1 because of parallel threshold
   - PDML disabled because object is not decorated with parallel clause

相同的结果。

即使我们从语句中删除 PDML 方面,SELECT(并行查询 - PQ)也会出现令人惊讶的结果。

select /*+ PARALLEL */ * from ParallelAuto;
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 2
select /*+ PARALLEL (AUTO) */ * from ParallelAuto;
Note
   - dynamic statistics used: dynamic sampling (level=2)
   - automatic DOP: Computed Degree of Parallelism is 1 because of parallel threshold

此非生产服务器上的活动非常有限。

PARALLEL (AUTO) 的这种行为似乎与文档(见下文)相矛盾。

Oracle SQL 数据库参考 | PARALLEL_DEGREE_POLICY

注意:如果在 SQL 语句级别使用 PARALLEL 提示,则无论 PARALLEL_DEGREE_POLICY 的值如何,都将启用自动并行度。

Oracle SQL 参考指南 |评论 |提示

此提示会覆盖 PARALLEL_DEGREE_POLICY 初始化参数的值。它适用于语句的 SELECT、INSERT、MERGE、UPDATE 和 DELETE 部分,以及表扫描部分。如果违反任何并行限制,则忽略提示。

12c

PARALLEL:语句始终并行运行,由数据库计算并行度,可以为2或更大。
PARALLEL (AUTO):数据库计算并行度,可以是1或更大。如果计算出的并行度为 1,则语句串行运行。
PARALLEL (MANUAL):优化器被强制使用语句中对象的并行设置。

19c/21c

PARALLEL:该语句导致并行度等于或大于计算的并行度,除非并行度对于最低成本计划不可行。当并行不可行时,语句串行运行。
PARALLEL (AUTO):该语句导致并行度等于或大于计算的并行度,除非并行度对于最低成本计划不可行。当并行不可行时,语句串行运行。
PARALLEL (MANUAL):优化器被强制使用语句中对象的并行设置。

这里发生了什么?提前致谢。

解决方法

如果估计的运行时间小于 PARALLEL(AUTO),则

PARALLEL_MIN_TIME_THRESHOLD 将不会启用并行性,begin dbms_stats.set_table_stats(user,'PARALLELAUTO',numrows => 99999999999); end; / 默认为 10 秒(也容易混淆地称为“AUTO”)。这种行为可能是一件好事,因为并行性会增加很多开销,并且并行性可能会不公平地使用大量资源来使快速语句仅稍微快一点。

您可以通过创建虚假行数并使优化器认为 SQL 需要很长时间来测试此行为:

PARALLEL_MIN_TIME_THRESHOLD

或者,您可以在会话或系统级别修改 alter session set parallel_min_time_threshold = 1; 。尽管由于您的测试表只有一行,因此可能没有任何足够低的值来触发并行性而不创建假行数。

<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             ....>

    <StackLayout>
        <Label Text="test" FontSize="{x:OnPlatform iOS='14',Android='12'}" />
    </StackLayout>
</ContentPage>

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...