2个场景实例讲解GaussDB(DWS)基表统计信息估算不准的处理方案

场景,实例,讲解,gaussdb,dws,统计,信息,估算,不准,处理,方案 · 浏览次数 : 119

小编点评

**生成内容时需要带简单的排版** **排版示例:** ``` 1 | -> Row Adapter | 195.504 | 1 | 1 | 227KB | | 321 | 675.14 2 | -> Vector Streaming (type: GATHER) | 195.491 | 1 | 1 | 873KB | | 321 | 675.14 3 | -> CStore Index Scan using mca_period_rate_u1 on mca_period_rate_t mca_rate2 | [164.344, 164.344] | 1 | 1 | [5MB, 5MB] | | 321 | 501.14 Predicate Information (identified by plan id) ---------------------------------------------------------------------------------------------------------------------------------------------------------- ``` **排版说明:** * 每条内容需要带简单的排版符号,例如 |、-、>。 * 排版符号之间需要用空格隔开。 * 排版示例仅供参考,您可以根据需要调整排版格式。

正文

摘要:通过2个实例场景讲解GaussDB(DWS)运维解决方案。

本文分享自华为云社区《GaussDB(DWS)运维 -- 基表统计信息估算不准的常见场景及处理方案》,作者:譡里个檔。

场景1:基表过滤字段存在的隐式类型时,基表行数估算偏小

这种场景绝大部分场景DWS能够处理,但是如果隐式类型转后的结果与统计信息中的字段枚举值的表达式不一样,就会导致估算的严重偏差

原始SQL如下

SELECT * FROM dmgrpdi.dwl_inv_res_rpt_ci_grp_f WHERE period_id=202212 AND source_flag=1;

对应的执行计划

                                                    QUERY PLAN
-------------------------------------------------------------------------------------------------------------------
  id |                            operation                             | E-rows | E-memory | E-width |  E-costs
 ----+------------------------------------------------------------------+--------+----------+---------+-----------
 1 | -> Row Adapter                                                  | 14160 | | 717 | 680025.43
 2 | ->  Vector Streaming (type: GATHER) | 14160 | | 717 | 680025.43
 3 | ->  Vector Partition Iterator                              | 14160 | 1MB      | 717 | 678241.33
 4 | ->  Partitioned CStore Scan on dwl_inv_res_rpt_ci_grp_f | 14160 | 1MB      | 717 | 678241.33
                  Predicate Information (identified by plan id)
 -------------------------------------------------------------------------------
 3 --Vector Partition Iterator
         Iterations: 1
 4 --Partitioned CStore Scan on dwl_inv_res_rpt_ci_grp_f
         Filter: ((period_id = 202212::numeric) AND ((source_flag)::bigint = 1))
         Pushdown Predicate Filter: (period_id = 202212::numeric)
         Partitions Selected by Static Prune: 36

发现source_flag字段上存在隐式类型转换,查询字段source_flag的统计信息

postgres=# SELECT most_common_vals,most_common_freqs, histogram_bounds  FROM pg_stats WHERE tablename = 'dwl_inv_res_rpt_ci_grp_f' AND attname = 'source_flag';
 most_common_vals | most_common_freqs | histogram_bounds
------------------+-----------------------------------+------------------
 {01,02,04,03}    | {.440034,.241349,.217413,.101089} | {05,06}
(1 row)

发现隐式类型转后的结果(1)与统计信息中的字段枚举值('01')的表达式不一样

处理方案:修改过滤条件,禁止类型转换,并且使用正确的常量值书写过滤条件

如上SQL语句中的source_flag=1修改为source_flag='01',修改后SQL语句如下

SELECT * FROM dmgrpdi.dwl_inv_res_rpt_ci_grp_f WHERE period_id=202212 AND source_flag='01';

查询新语句的执行计划

                                                      QUERY PLAN
----------------------------------------------------------------------------------------------------------------------
  id |                            operation                             |  E-rows | E-memory | E-width |  E-costs
 ----+------------------------------------------------------------------+-----------+----------+---------+-----------
 1 | -> Row Adapter                                                  | 108359075 | | 717 | 480542.98
 2 | ->  Vector Streaming (type: GATHER) | 108359075 | | 717 | 480542.98
 3 | ->  Vector Partition Iterator                              | 108359075 | 1MB      | 717 | 478758.88
 4 | ->  Partitioned CStore Scan on dwl_inv_res_rpt_ci_grp_f | 108359075 | 1MB      | 717 | 478758.88
                           Predicate Information (identified by plan id)
 -------------------------------------------------------------------------------------------------
 3 --Vector Partition Iterator
         Iterations: 1
 4 --Partitioned CStore Scan on dwl_inv_res_rpt_ci_grp_f
         Filter: ((period_id = 202212::numeric) AND (source_flag = '01'::text))
         Pushdown Predicate Filter: ((period_id = 202212::numeric) AND (source_flag = '01'::text))
         Partitions Selected by Static Prune: 36

场景2:基表在多列组合主键上过滤时,基表行数估算偏大

这种场景是因为DWS对基表上多个过滤条件之间采取弱相关性处理,当多个过滤条件是主键时,可能导致结果集估算偏大。

原始SQL如下

SELECT * FROM mca.mca_period_rate_t mca_rate2
WHERE period_number = '202208' AND from_currency_code = 'RMB' AND to_currency_code = 'USD'

执行信息如下

 id |                      operation                       |       A-time | A-rows | E-rows | Peak Memory | E-memory | A-width | E-width | E-costs  
----+------------------------------------------------------+--------------------+--------+--------+-------------+----------+---------+---------+----------
 1 | -> Row Adapter                                      | 444.735 | 1 | 2033 | 227KB       | | | 321 | 22601.41 
 2 | ->  Vector Streaming (type: GATHER) | 444.720 | 1 | 2033 | 873KB       | | | 321 | 22601.41 
 3 | -> CStore Scan on mca_period_rate_t mca_rate2 | [435.167, 435.167] | 1 | 2033 | [5MB, 5MB] | 1MB      | | 321 | 22427.41 
                                                              Predicate Information (identified by plan id) 
-------------------------------------------------------------------------------------------------------------------------------------------------------------------------
 3 --CStore Scan on mca_period_rate_t mca_rate2
        Filter: (((period_number)::text = '202208'::text) AND ((from_currency_code)::text = 'RMB'::text) AND ((to_currency_code)::text = 'USD'::text))
 Rows Removed by Filter: 425812
        Pushdown Predicate Filter: (((period_number)::text = '202208'::text) AND ((from_currency_code)::text = 'RMB'::text) AND ((to_currency_code)::text = 'USD'::text))

可以发现基表mca.mca_period_rate_t的行数估算严重偏大。

使用如下SQL语句查看表mca.mca_period_rate_t的定义

SELECT pg_get_tabledef('mca.mca_period_rate_t'::regclass);

查询表mca.mca_period_rate_t定义

SELECT pg_get_tabledef('mca.mca_period_rate_t');
SET search_path = mca;
CREATE TABLE mca_period_rate_t (
seq numeric NOT NULL,
period_number character varying(10) NOT NULL,
from_currency_code character varying(20) NOT NULL,
to_currency_code character varying(20) NOT NULL,
begin_rate numeric(35,18),
end_rate numeric(35,18),
avg_rate numeric(35,18),
creation_date timestamp(0) without time zone NOT NULL,
created_by numeric NOT NULL,
last_update_date timestamp(0) without time zone,
last_updated_by numeric,
rmb_begin_rate numeric(35,18),
usd_begin_rate numeric(35,18),
rmb_end_rate numeric(35,18),
usd_end_rate numeric(35,18),
rmb_avg_rate numeric(35,18),
usd_avg_rate numeric(35,18),
crt_cycle_id numeric,
crt_job_instance_id numeric,
last_upd_cycle_id numeric,
upd_job_instance_id numeric,
cdc_key_id character varying(128) DEFAULT sys_guid(),
end_rate2 numeric(35,18),
avg_rate2 numeric(35,18),
last_period_end_rate numeric(35,18)
)
WITH (orientation=column, compression=low, colversion=2.0, enable_delta=false)
DISTRIBUTE BY REPLICATION
TO GROUP group_version1;
CREATE UNIQUE INDEX mca_period_rate_u1 ON mca.mca_period_rate_t USING cbtree (period_number, from_currency_code, to_currency_code) TABLESPACE pg_default;

发现 (period_number, from_currency_code, to_currency_code) 为组合的唯一索引。

处理方案:对组合索引列收多列统计信息

注意此种方案只适用在基表比较小的情况下。因为多列统计信息需要使用百分比采样的方式计算统计信息,当表比较大时,统计信息计算耗时回很长。

针对如上查询语句执行如下语句收集(period_number, from_currency_code, to_currency_code) 多列统计信息

ANALYZE mca.mca_period_rate_t((period_number, from_currency_code, to_currency_code));

收集多列统计信息之后,基表的行数估算恢复正产

 id |                                      operation                                      |       A-time | A-rows | E-rows | Peak Memory | A-width | E-width | E-costs 
----+-------------------------------------------------------------------------------------+--------------------+--------+--------+-------------+---------+---------+---------
 1 | -> Row Adapter                                                                     | 195.504 | 1 | 1 | 227KB       | | 321 | 675.14 
 2 | ->  Vector Streaming (type: GATHER) | 195.491 | 1 | 1 | 873KB       | | 321 | 675.14 
 3 | -> CStore Index Scan using mca_period_rate_u1 on mca_period_rate_t mca_rate2 | [164.344, 164.344] | 1 | 1 | [5MB, 5MB] | | 321 | 501.14 
                                                      Predicate Information (identified by plan id) 
----------------------------------------------------------------------------------------------------------------------------------------------------------
 3 --CStore Index Scan using mca_period_rate_u1 on mca_period_rate_t mca_rate2
 Index Cond: (((period_number)::text = '202208'::text) AND ((from_currency_code)::text = 'RMB'::text) AND ((to_currency_code)::text = 'USD'::text))

 

点击关注,第一时间了解华为云新鲜技术~

与2个场景实例讲解GaussDB(DWS)基表统计信息估算不准的处理方案相似的内容:

2个场景实例讲解GaussDB(DWS)基表统计信息估算不准的处理方案

摘要:通过2个实例场景讲解GaussDB(DWS)运维解决方案。 本文分享自华为云社区《GaussDB(DWS)运维 -- 基表统计信息估算不准的常见场景及处理方案》,作者:譡里个檔。 场景1:基表过滤字段存在的隐式类型时,基表行数估算偏小 这种场景绝大部分场景DWS能够处理,但是如果隐式类型转后的

[转帖]长篇图解 etcd 核心应用场景及编码实战

https://xie.infoq.cn/article/3329de088beb60f5803855895 一、白话 etcd 与 zookeeper 二、etcd 的 4 个核心机制 三、Leader 选举与客户端交互 四、etcd 的应用场景 4.1. kubernetes 大脑 4.2. 服

实现并发新高度:23ai的无锁列值保留

Oracle Database 23ai支持Lock-Free Reservation,中文通常译为“无锁列值保留”。 本文将通过3个部分来阐述Lock-Free Reservation的这个特性: 1.应用场景 2.实现原理 3.使用限制 1.应用场景 Lock-Free Reservation这

活字格性能优化技巧(2)-如何在大规模数据量的场景下提升数据访问效率

本文由葡萄城技术团队于博客园原创并首发转载请注明出处:葡萄城官网,葡萄城为开发者提供专业的开发工具、解决方案和服务,赋能开发者。 在上节内容中我们介绍了如何利用数据库主键提升访问性能,本节内容我们继续为大家介绍如何在大规模数据量的场景下提升数据访问效率。 在开始之前先做个小小的实验: 1. 准备一张

ThreadLocal:线程中的全局变量

最近接了一个新需求,业务场景上需要在原有基础上新增2个字段,接口新增参数意味着很多类和方法的逻辑都需要改变,需要先判断是否属于该业务场景,再做对应的逻辑。原本的打算是在入口处新增变量,在操作数据的时候进行逻辑判断将变量进行存储或查询。

element-ui使用el-date-picker日期组件常见场景

开始 最近一直在使用 element-ui中的日期组件。 所以想对日期组件常用的做一个简单的总结; 1.处理日期组件选择的时候面板联动问题 2.限制时间范围 解除两个日期面板之间的联动 我们发现2个日期面板之间其实是有联动关系的; 开始时间面板和结束时间面板始终只能相邻; 不能出现开始时间选择3月,

Redis set数据类型命令使用及应用场景使用总结

转载请注明出处: 目录 1.sadd 集合添加元素 2.srem移除元素 3.smembers 获取key的所有元素 4.scard 获取key的个数 5.sismember 判断member元素是否存在集合key中 6.srandmember key count 从集合key中随机选出count个

分享下最近基于Avalonia UI和MAUI写跨平台时间管理工具的体验

起因 几个月前,我在寻找一款时间管理软件,类似番茄时钟的工具,但是希望可以自定义时间。 需要自定义的场景 做雅思阅读,3篇文件需要严格控制时间分配,需要一个灵活的计时器 定期提醒,每30分钟需要喝水或者上个厕所或者摸一下鱼... 总结起来就是:专注一段时间,比如30分钟,然后休息10分钟,且没有杂七

[转帖]谈谈ClickHouse性能情况以及相关优化

https://zhuanlan.zhihu.com/p/349105024 ClickHouse性能情况 主要分为4个方面 1、单个查询吞吐量 场景一: 如果数据被放置在page cache中,则一个不太复杂的查询在单个服务器上大约能够以2-10GB/s(未压缩)的速度进行处理(对于简单的查询,速

[转帖]Vxlan基础理解

一 . 为什么需要Vxlan 1. vlan的数量限制 4096个vlan远不能满足大规模云计算数据中心的需求 2. 物理网络基础设施的限制 基于IP子网的区域划分限制了需要二层网络连通性的应用负载的部署 3. TOR交换机MAC表耗尽 虚拟化以及东西向流量导致更多的MAC表项 4. 多租户场景 I