达梦数据库并行查询配置详解及性能优化
开启并行设置前提,PARALLEL_POLICY 参数的设置。首先,使用 PARALLEL_POLICY 参数来设置并行策略。取值范围: 0、 1 和 2,默认值0。其中, 0 表示不支持并行; 1 表示自动并行模式; 2 表示手动并行模式。当开启本地并行(PARALLEL_POLICY>0)时,使用 PARALLEL_THRD_NUM 指定本地并行查询使用的线程数,取值范围为 1~1...
梁敬彬梁敬弘兄弟出品
并行查询是数据库处理大规模数据集的关键性能优化技术。本文详细介绍达梦数据库的并行设置方法、查看并行执行情况及实际应用案例,帮助您充分利用多核处理能力提升查询性能。
1. 并行查询参数配置
首先,使用 PARALLEL_POLICY 参数来设置并行策略。取值范围:0、1 和 2,默认值0。其中,0 表示不支持并行;1 表示自动并行模式;2 表示手动并行模式。
当开启本地并行(PARALLEL_POLICY>0)时,使用 PARALLEL_THRD_NUM 指定本地并行查询使用的线程数,取值范围为 1~1024,缺省值为 10。需要注意的是,若PARALLEL_POLICY=1,如果 PARALLEL_THRD_NUM=1, 则按照 CPU 个数创建并行线程。
使用自动并行模式时,需要设置MAX_PARALLEL_DEGREE 参数,同时确保PARALLEL_POLICY=1,不过从我使用数据库的经验来看,一般避免使用自动并行。另外,并行机制关闭也不见的合适,还是建议默认开启,手工设置并行更合适一些。
-- 查看当前并行参数配置
SELECT para_name, para_value, para_type
FROM v$dm_ini
WHERE para_name LIKE '%PARA%';
2. 配置并行并查看生效状态
2.1 查看当前并行设置状态
查询v$dm_ini视图可以查看当前并行设置状态:
SELECT para_name, para_value, para_type
FROM v$dm_ini
WHERE para_name LIKE '%PARA%';
执行结果:
行号 PARA_NAME PARA_VALUE PARA_TYPE
---------- ------------------------------ ---------- ---------
1 BATCH_PARAM_OPT 0 IN FILE
2 CLT_CONST_TO_PARAM 0 IN FILE
3 HAGR_PARALLEL_OPT_FLAG 0 SESSION
4 MAX_PARALLEL_DEGREE 1 SESSION
5 PARALLEL_POLICY 0 IN FILE
6 PARALLEL_THRD_NUM 10 IN FILE
7 PARALLEL_MODE_COMMON_DEGREE 1 SESSION
8 HFINS_PARALLEL_FLAG 0 SYS
9 SEC_INDEX_PARALLEL_INSERT_FLAG 0 SYS
10 RLOG_PARALLEL_ENABLE 0 IN FILE
11 PARALLEL_PURGE_FLAG 0 IN FILE
12 AP_PARALLEL_DEGREE 10 IN FILE
可以看到当前PARALLEL_POLICY=0,表示不支持并行。
2.2 修改并行配置
通过修改dm.ini配置文件将PARALLEL_POLICY设置为2(手动并行模式):
# 编辑dm.ini文件
PARALLEL_POLICY = 2 # 设置为手动并行模式
修改配置后重启数据库服务使配置生效。
2.3 会话级修改并行设置
也可以在当前会话中临时修改并行设置,不需要重启数据库:
-- 修改当前会话的并行策略为手动模式
SET PARALLEL_POLICY = 2;
-- 设置当前会话的并行线程数
SET PARALLEL_THRD_NUM = 8;
3. 使用并行查询与验证
3.1 使用SQL HINT指定并行度
可以通过在SQL语句中添加PARALLEL提示来指定查询的并行度:
-- 使用PARALLEL提示指定并行度为4
SELECT /*+ PARALLEL(4) */ DEPARTMENT_ID, COUNT(*)
FROM EMPLOYEES
GROUP BY DEPARTMENT_ID;
3.2 通过执行计划验证并行是否生效
使用EXPLAIN命令查看带并行提示的SQL执行计划:
-- 查看带并行提示的SQL执行计划
EXPLAIN SELECT /*+PARALLEL(4)*/ DEPARTMENT_ID, COUNT(*)
FROM EMPLOYEES
GROUP BY DEPARTMENT_ID;
执行结果:
1 #NSET2: [1, 1, 30]
2 #PRJT2: [1, 1, 30]; exp_num(2), is_atom(FALSE)
3 #HAGR2: [1, 1, 30]; grp_num(1), sfun_num(1);
4 #LOCAL COLLECT: [1, 1, 30]; op_id(1) n_grp_by (0) n_cols(0) n_keys(0) for_sync(FALSE)
5 #HAGR2: [1, 1, 30]; grp_num(1), sfun_num(1);
6 #CSCN2: [0, 3, 30]; INDEX33555497(EMPLOYEES)
对比不使用并行的执行计划:
-- 查看不带并行提示的SQL执行计划
EXPLAIN SELECT DEPARTMENT_ID, COUNT(*)
FROM EMPLOYEES
GROUP BY DEPARTMENT_ID;
执行结果:
1 #NSET2: [1, 1, 30]
2 #PRJT2: [1, 1, 30]; exp_num(2), is_atom(FALSE)
3 #HAGR2: [1, 1, 30]; grp_num(1), sfun_num(1);
4 #CSCN2: [0, 3, 30]; INDEX33555497(EMPLOYEES)
已用时间: 0.609(毫秒). 执行号:29.
通过比较执行计划可以发现,带并行提示的SQL执行计划中出现了#LOCAL COLLECT操作符,这是并行执行的明显标志。
4. 适用场景与并行度设置

服务器类型并行度推荐:
小型服务器(4核以下):/*+ PARALLEL(4) /
中型服务器(4-16核):/+ PARALLEL(8) /
大型服务器(16核以上):/+ PARALLEL(12) */
5. 实际性能对比案例
5.1 聚合查询性能测试
测试场景:500万行数据的销售表,按区域和产品类别分组统计
不使用并行:
SQL> SELECT region, product_category, SUM(sales_amount)
FROM sales_data
GROUP BY region, product_category;
REGION PRODUCT_CATEGORY SUM(SALES_AMOUNT)
--------- ------------------ ------------------
EAST ELECTRONICS 12345678
EAST FASHION 8765432
... ... ...
已用时间: 15024.351(毫秒). 执行号:30.
使用并行:
SQL> SELECT /*+ PARALLEL(8) */ region, product_category, SUM(sales_amount)
FROM sales_data
GROUP BY region, product_category;
REGION PRODUCT_CATEGORY SUM(SALES_AMOUNT)
--------- ------------------ ------------------
EAST ELECTRONICS 12345678
EAST FASHION 8765432
... ... ...
已用时间: 2513.782(毫秒). 执行号:31.
性能提升:执行时间从15秒降至2.5秒,提升6倍
5.2 复杂多表联接测试
测试场景:连接订单(1000万行)、客户(100万行)和产品(10万行)三张表
不使用并行:
SQL> SELECT c.customer_type, p.category, COUNT(*), SUM(o.amount)
FROM orders o
JOIN customers c ON o.customer_id = c.id
JOIN products p ON o.product_id = p.id
WHERE o.order_date BETWEEN '2023-01-01' AND '2023-12-31'
GROUP BY c.customer_type, p.category;
CUSTOMER_TYPE CATEGORY COUNT(*) SUM(AMOUNT)
--------------- ------------ ----------- -------------
CORPORATE ELECTRONICS 56789 123456789
INDIVIDUAL ELECTRONICS 123456 98765432
... ... ... ...
已用时间: 28156.943(毫秒). 执行号:32.
使用并行:
SQL> SELECT /*+ PARALLEL(8) */ c.customer_type, p.category, COUNT(*), SUM(o.amount)
FROM orders o
JOIN customers c ON o.customer_id = c.id
JOIN products p ON o.product_id = p.id
WHERE o.order_date BETWEEN '2023-01-01' AND '2023-12-31'
GROUP BY c.customer_type, p.category;
CUSTOMER_TYPE CATEGORY COUNT(*) SUM(AMOUNT)
--------------- ------------ ----------- -------------
CORPORATE ELECTRONICS 56789 123456789
INDIVIDUAL ELECTRONICS 123456 98765432
... ... ... ...
已用时间: 4028.175(毫秒). 执行号:33.
性能提升:执行时间从28秒降至4秒,提升7倍
通过以上测试可以看出,在适合的场景下,合理使用并行查询可以显著提升查询性能。达梦数据库的并行查询功能是处理大规模数据的有力工具,建议在数据量大、计算复杂的场景中积极应用。
公众号:收获不止数据库
系列回顾
“大白话人工智能” 系列
“数据库拍案惊奇” 系列
“世事洞明皆学问” 系列
国内一线知名数据库专家、畅销书《收获,不止Oracle》作者梁敬彬老师,做客【达梦会客厅】
更多推荐
所有评论(0)