CBO 统计信息
本文介绍 StarRocks CBO 优化器(Cost-based Optimizer)的基本概念,以及如何为 CBO 优化器采集统计信息来优化查询计划。StarRocks 2.4 版本引入直方图作为统计信息,提供更准确的数据分布统计。
3.2 之前版本支持对 StarRocks 内表采集统计信息。从 3.2 版本起,支持采集 Hive,Iceberg,Hudi 表的统计信息,无需依赖其他系统。
什么是 CBO 优化器
CBO 优化器是查询优化的关键。一条 SQL 查询到达 StarRocks 后,会解析为一条逻辑执行计划,CBO 优化器对逻辑计划进行改写和转换,生成多个物理执行计划。通过估算计划中每个算子的执行代价(CPU、内存、网络、I/O 等资源消耗),选择代价最低的一条查询路径作为最终的物理查询计划。
StarRocks CBO 优化器采用 Cascades 框架,基于多种统计信息进行代价估算,能够在数万级别的执行计划中,选择代价最低的执行计划,提升复杂查询的效率和性能。StarRocks 1.16.0 版本推出自研的 CBO 优化器。1.19 版本及以上,该特性默认开启。
统计信息是 CBO 优化器的重要组成部分,统计信息的准确与否决定了代价估算是否准确,对于 CBO 选择最优 Plan 至关重要,进而决定了 CBO 优化器的性能好坏。下文详细介绍统计信息的类型、采集策略、以及如何创建采集任务和查看统计信息。
统计信息数据类型
StarRocks 会采集多种统计信息,为查询优化提供代价估算的参考。
基础统计信息
StarRocks 默认定期采集表和列的如下基础信息:
-
row_count: 表的总行数
-
data_size: 列的数据大小
-
ndv: 列基数,即 distinct value 的个数
-
null_count: 列中 NULL 值的个数
-
min: 列的最小值
-
max: 列的最大值
全量的统计信息存储在 StarRocks 集群 _statistics_ 数据库下的 column_statistics 表中,您可以在 _statistics_ 数据库下查看。查询时会返回类似如下信息:
SELECT * FROM _statistics_.column_statistics\G
*************************** 1. row ***************************
table_id: 10174
partition_id: 10170
column_name: is_minor
db_id: 10169
table_name: zj_test.source_wiki_edit
partition_name: p06
row_count: 2
data_size: 2
ndv: NULL
null_count: 0
max: 1
min: 0
直方图
从 2.4 版本开始,StarRocks 引入直方图 (Histogram)。直方图常用于估算数据分布,当数据存在倾斜时,直方图可以弥补基础统计信息估算存在的偏差,输出更准确的数据分布信息。
StarRocks 采用等深直方图 (Equi-height Histogram),即选定若干个 bucket,每个 bucket 中的数据量几乎相等。对于出现频次较高、对选择率(selectivity)影响较大的数值,StarRocks 会分配单独的桶进行存储。桶数量越多时,直方图的估算精度就越高,但是也会增加统计信息的内存使用。您可以根据业务情况调整直方图的桶个数和单个采集任务的 MCV(most common value)个数。
直方图适用于有明显数据倾斜,并且有频繁查询请求的列。如果您的表数据分布比较均匀,可以不使用直方图。直方图支持的列类型为数值类型、DATE、DATETIME 或字符串类型。
直方图统计信息存储在 StarRocks 集群 _statistics_ 数据库的 histogram_statistics 表中。查询时会返回类似如下信息:
SELECT * FROM _statistics_.histogram_statistics\G
*************************** 1. row ***************************
table_id: 10174
column_name: added
db_id: 10169
table_name: zj_test.source_wiki_edit
buckets: NULL
mcv: [["23","1"],["5","1"]]
update_time: 2023-12-01 15:17:10.274000