- 关于 TiDB
- 快速上手
- 部署集群
- 数据迁移
- 数据迁移概述
- 从 MySQL 迁移至 TiDB
- 从 CSV 文件迁移至 TiDB
- 运维操作
- 监控与告警
- 故障诊断
- 性能调优
- 系统调优
- 软件调优
- SQL 性能调优
- 教程
- TiDB 生态工具
- TiDB 生态工具功能概览
- TiDB 生态工具适用场景
- TiDB 工具下载
- Backup & Restore (BR)
- TiDB Binlog
- TiDB Lightning
- TiCDC 简介
- Dumpling 使用文档
- sync-diff-inspector
- Loader 使用文档
- Mydumper 使用文档
- Syncer 使用文档
- TiSpark
- 参考指南
- 架构
- 监控指标
- 安全加固
- 权限
- SQL
- SQL 语言结构和语法
- 属性
- 字面值
- Schema 对象名
- 关键字
- 用户自定义变量
- 表达式语法
- 注释语法
- SQL 语句
- ADD COLUMN
- ADD INDEX
- ADMIN
- ALTER DATABASE
- ALTER INSTANCE
- ALTER TABLE
- ALTER USER
- ANALYZE
- BACKUP
- BEGIN
- CHANGE COLUMN
- CHANGE DRAINER
- CHANGE PUMP
- COMMIT
- CREATE [GLOBAL|SESSION] BINDING
- CREATE DATABASE
- CREATE INDEX
- CREATE ROLE
- CREATE SEQUENCE
- CREATE TABLE LIKE
- CREATE TABLE
- CREATE USER
- CREATE VIEW
- DEALLOCATE
- DELETE
- DESC
- DESCRIBE
- DO
- DROP [GLOBAL|SESSION] BINDING
- DROP COLUMN
- DROP DATABASE
- DROP INDEX
- DROP ROLE
- DROP SEQUENCE
- DROP STATS
- DROP TABLE
- DROP USER
- DROP VIEW
- EXECUTE
- EXPLAIN ANALYZE
- EXPLAIN
- FLASHBACK TABLE
- FLUSH PRIVILEGES
- FLUSH STATUS
- FLUSH TABLES
- GRANT
- GRANT
- INSERT
- KILL [TIDB]
- LOAD STATS
- MODIFY COLUMN
- PREPARE
- RECOVER TABLE
- RENAME INDEX
- RENAME TABLE
- REPLACE
- RESTORE
- REVOKE
- REVOKE
- ROLLBACK
- SELECT
- SET DEFAULT ROLE
- SET [NAMES|CHARACTER SET]
- SET PASSWORD
- SET ROLE
- SET TRANSACTION
- SET [GLOBAL|SESSION]
- SHOW [BACKUPS|RESTORES]
- SHOW ANALYZE STATUS
- SHOW [GLOBAL|SESSION] BINDINGS
- SHOW BUILTINS
- SHOW CHARACTER SET
- SHOW COLLATION
- SHOW [FULL] COLUMNS FROM
- SHOW CONFIG
- SHOW CREATE SEQUENCE
- SHOW CREATE TABLE
- SHOW CREATE USER
- SHOW DATABASES
- SHOW DRAINER STATUS
- SHOW ENGINES
- SHOW ERRORS
- SHOW [FULL] FIELDS FROM
- SHOW GRANTS
- SHOW INDEX [FROM|IN]
- SHOW INDEXES [FROM|IN]
- SHOW KEYS [FROM|IN]
- SHOW MASTER STATUS
- SHOW PLUGINS
- SHOW PRIVILEGES
- SHOW [FULL] PROCESSLIST
- SHOW PROFILES
- SHOW PUMP STATUS
- SHOW SCHEMAS
- SHOW STATS_HEALTHY
- SHOW STATS_HISTOGRAMS
- SHOW STATS_META
- SHOW [GLOBAL|SESSION] STATUS
- SHOW TABLE NEXTROWID
- SHOW TABLE REGIONS
- SHOW TABLE STATUS
- SHOW [FULL] TABLES
- SHOW [GLOBAL|SESSION] VARIABLES
- SHOW WARNINGS
- SHUTDOWN
- Split Region 使用文档
- START TRANSACTION
- TRACE
- TRUNCATE
- UPDATE
- USE
- 数据类型
- 函数与操作符
- 约束
- 生成列
- SQL 模式
- 事务
- 垃圾回收 (GC)
- 视图
- 分区表
- 字符集和排序规则
- 系统表
- TiDB 系统表
- INFORMATION_SCHEMA
- TiDB 简介
- ANALYZE_STATUS
- CHARACTER_SETS
- CLUSTER_CONFIG
- CLUSTER_HARDWARE
- CLUSTER_INFO
- CLUSTER_LOAD
- CLUSTER_LOG
- CLUSTER_SYSTEMINFO
- COLLATIONS
- COLLATIONCHARACTERSET_APPLICABILITY
- COLUMNS
- DDL_JOBS
- ENGINES
- INSPECTION_RESULT
- INSPECTION_RULES
- INSPECTION_SUMMARY
- KEYCOLUMNUSAGE
- METRICS_SUMMARY
- METRICS_TABLES
- PARTITIONS
- PROCESSLIST
- SCHEMATA
- SEQUENCES
- SESSION_VARIABLES
- SLOW_QUERY
- STATISTICS
- TABLES
- TABLE_CONSTRAINTS
- TABLESTORAGESTATS
- TIDBHOTREGIONS
- TIDB_INDEXES
- TIDBSERVERSINFO
- TIFLASH_REPLICA
- TIKVREGIONPEERS
- TIKVREGIONSTATUS
- TIKVSTORESTATUS
- USER_PRIVILEGES
- VIEWS
- Metrics Schema
- SQL 语言结构和语法
- UI
- CLI
- 命令行参数
- 配置文件参数
- 系统变量
- 存储引擎
- TiUP
- 遥测
- 错误码与故障诊断
- TiCDC Open Protocol
- 通过拓扑 label 进行副本调度
- 常见问题解答 (FAQ)
- 术语表
统计信息简介
在索引的选择章节中,提到了 TiDB 会使用统计信息来决定选择哪个索引。在 TiDB 中,我们维护的统计信息包括表的总行数,列的等深直方图,Count-Min Sketch,Null 值的个数,平均长度,不同值的数目等等。本文将简单介绍直方图和 Count-Min Sketch,以及详细介绍统计信息的收集和维护。
直方图简介
直方图是一种对数据分布情况进行描述的工具,它会按照数据的值大小进行分桶,并用一些简单的数据来描述每个桶,比如落在桶里的值的个数。在 TiDB 中,会对每个表具体的列构建一个等深直方图,区间查询的估算便是借助该直方图来进行。
等深直方图,就是让落入每个桶里的值数量尽量相等。举个例子,比方说对于给定的集合 {1.6, 1.9, 1.9, 2.0, 2.4, 2.6, 2.7, 2.7, 2.8, 2.9, 3.4, 3.5},并且生成 4 个桶,那么最终的等深直方图就会如下图所示,包含四个桶 [1.6, 1.9],[2.0, 2.6],[2.7, 2.8],[2.9, 3.5],其桶深均为 3。
在Count-Min Sketch
Count-Min Sketch 是一种哈希结构,当查询中出现诸如 a = 1
或者 IN
查询(如 a in (1, 2, 3)
)这样的等值查询时,TiDB 便会使用这个数据结构来进行估算。
由于 Count-Min Sketch 是一个哈希结构,就有出现哈希碰撞的可能。当在 EXPLAIN
语句中发现等值查询的估算偏离实际值较大时,就可以认为是一个比较大的值和一个比较小的值被哈希到了一起。这时有以下两种手段来避免这个情况:
- 修改统计信息的收集
手动收集
可以通过执行
ANALYZE
语句来收集统计信息。全量收集
注意:
在 TiDB 中执行
ANALYZE TABLE
语句比在 MySQL 或 InnoDB 中耗时更长。InnoDB 采样的只是少量页面,但 TiDB 会完全重构一系列统计信息。适用于 MySQL 的脚本会误以为执行ANALYZE TABLE
耗时较短。如需更快的分析速度,可将
tidb_enable_fast_analyze
设置为1
来打开快速分析功能。该参数的默认值为0
。快速分析功能开启后,TiDB 会随机采样约 10000 行的数据来构建统计信息。因此在数据分布不均匀或者数据量比较少的情况下,统计信息的准确度会比较差。可能导致执行计划不优,比如选错索引。如果可以接受普通
ANALYZE
语句的执行时间,则推荐关闭快速分析功能。可以通过以下几种语法进行全量收集。
收集 TableNameList 中所有表的统计信息:
ANALYZE TABLE TableNameList [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
WITH NUM BUCKETS
用于指定生成直方图的桶数量上限。WITH NUM TOPN
用于指定生成 TOPN 数目的上限。WITH NUM CMSKETCH DEPTH
用于指定 CM Sketch 的长。WITH NUM CMSKETCH WIDTH
用于指定 CM Sketch 的宽。WITH NUM SAMPLES
用于指定采样的数目。
收集 TableName 中所有的 IndexNameList 中的索引列的统计信息:
ANALYZE TABLE TableName INDEX [IndexNameList] [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
IndexNameList 为空时会收集所有索引列的统计信息。
收集 TableName 中所有的 PartitionNameList 中分区的统计信息:
ANALYZE TABLE TableName PARTITION PartitionNameList [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
收集 TableName 中所有的 PartitionNameList 中分区的索引列统计信息:
ANALYZE TABLE TableName PARTITION PartitionNameList [IndexNameList] [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
增量收集
对于类似时间列这样的单调不减列,在进行全量收集后,可以使用增量收集来单独分析新增的部分,以提高分析的速度。
注意:
- 目前只有索引提供了增量收集的功能
- 使用增量收集时,必须保证表上只有插入操作,且应用方需要保证索引列上新插入的值是单调不减的,否则会导致统计信息不准,影响 TiDB 优化器选择合适的执行计划
可以通过以下几种语法进行增量收集。
增量收集 TableName 中所有的 IndexNameList 中的索引列的统计信息:
ANALYZE INCREMENTAL TABLE TableName INDEX [IndexNameList] [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
增量收集 TableName 中所有的 PartitionNameList 中分区的索引列统计信息:
ANALYZE INCREMENTAL TABLE TableName PARTITION PartitionNameList INDEX [IndexNameList] [WITH NUM BUCKETS|TOPN|CMSKETCH DEPTH|CMSKETCH WIDTH|SAMPLES];
自动更新
在发生增加,删除以及修改语句时,TiDB 会自动更新表的总行数以及修改的行数。这些信息会定期持久化下来, 更新的周期是 20 *
stats-lease
,stats-lease
的默认值是 3s,如果将其指定为 0,那么将不会自动更新。和统计信息自动更新相关的三个系统变量如下:
系统变量名 默认值 功能 tidb_auto_analyze_ratio
0.5 自动更新阈值 tidb_auto_analyze_start_time
00:00 +0000
一天中能够进行自动更新的开始时间 tidb_auto_analyze_end_time
23:59 +0000
一天中能够进行自动更新的结束时间 当某个表
tbl
的修改行数与总行数的比值大于tidb_auto_analyze_ratio
,并且当前时间在tidb_auto_analyze_start_time
和tidb_auto_analyze_end_time
之间时,TiDB 会在后台执行ANALYZE TABLE tbl
语句自动更新这个表的统计信息。在查询语句执行时,TiDB 会以
feedback-probability
的概率收集反馈信息,并将其用于更新直方图和 Count-Min Sketch。可通过配置文件修改feedback-probability
,其默认值是0.05
。设置成0.0
可以关闭这个功能。注意:
在配置文件中如果将
feedback-probability
设置为0
会导致设置失败并报错。需要设置成0.0
才可以关闭feedback-probability
。控制 ANALYZE 并发度
执行 ANALYZE 语句的时候,你可以通过一些参数来调整并发度,以控制对系统的影响。
tidb_build_stats_concurrency
目前 ANALYZE 执行的时候会被切分成一个个小的任务,每个任务只负责某一个列或者索引。
tidb_build_stats_concurrency
可以控制同时执行的任务的数量,其默认值是 4。tidb_distsql_scan_concurrency
在执行分析普通列任务的时候,
tidb_distsql_scan_concurrency
可以用于控制一次读取的 Region 数量,其默认值是 15。tidb_index_serial_scan_concurrency
在执行分析索引列任务的时候,
tidb_index_serial_scan_concurrency
可以用于控制一次读取的 Region 数量,其默认值是 1。查看 ANALYZE 状态
在执行
ANALYZE
时,可以通过 SQL 语句来查看当前ANALYZE
的状态。语法如下:
SHOW ANALYZE STATUS [ShowLikeOrWhere];
该语句会输出
ANALYZE
的状态,可以通过使用ShowLikeOrWhere
来筛选需要的信息。目前
SHOW ANALYZE STATUS
会输出 7 列,具体如下:语法元素 说明 table_schema 数据库名 table_name 表名 partition_name 分区名 job_info 任务具体信息。如果分析索引则会包含索引名 row_count 已经分析的行数 start_time 任务开始执行的时间 state 任务状态,包括 pending(等待)、running(正在执行)、finished(执行成功)和 failed(执行失败) 统计信息的查看
你可以通过一些语句来查看统计信息的状态。
表的元信息
你可以通过
SHOW STATS_META
来查看表的总行数以及修改的行数等信息。语法如下:
其中,
ShowLikeOrWhereOpt
部分的语法图为:SHOW STATS_META [ShowLikeOrWhere];
目前
SHOW STATS_META
会输出 6 列,具体如下:语法元素 说明 db_name 数据库名 table_name 表名 partition_name 分区名 update_time 更新时间 modify_count 修改的行数 row_count 总行数 注意:
在 TiDB 根据 DML 语句自动更新总行数以及修改的行数时,
update_time
也会被更新,因此并不能认为update_time
是最近一次发生 Analyze 的时间。表的健康度信息
通过
SHOW STATS_HEALTHY
可以查看表的统计信息健康度,并粗略估计表上统计信息的准确度。当modify_count
>=row_count
时,健康度为 0;当modify_count
<row_count
时,健康度为 (1 -modify_count
/row_count
) * 100。SHOW STATS_HEALTHY
的语法图为:其中,
ShowLikeOrWhereOpt
部分的语法图为:目前,
SHOW STATS_HEALTHY
会输出 4 列,具体如下:语法元素 说明 db_name 数据库名 table_name 表名 partition_name 分区名 healthy 健康度 列的元信息
你可以通过
SHOW STATS_HISTOGRAMS
来查看列的不同值数量以及 NULL 数量等信息。语法如下:
SHOW STATS_HISTOGRAMS [ShowLikeOrWhere];
该语句会输出所有列的不同值数量以及 NULL 数量等信息,你可以通过 ShowLikeOrWhere 来筛选需要的信息。
目前
SHOW STATS_HISTOGRAMS
会输出 8 列,具体如下:语法元素 说明 db_name 数据库名 table_name 表名 partition_name 分区名 column_name 根据 is_index 来变化:is_index 为 0 时是列名,为 1 时是索引名 is_index 是否是索引列 update_time 更新时间 distinct_count 不同值数量 null_count NULL 的数量 avg_col_size 列平均长度 直方图桶的信息
你可以通过
SHOW STATS_BUCKETS
来查看直方图每个桶的信息。语法如下:
SHOW STATS_BUCKETS [ShowLikeOrWhere];
语法图:
SHOW STATUS_BUCKETS:
该语句会输出所有桶的信息,你可以通过 ShowLikeOrWhere 来筛选需要的信息。
目前
SHOW STATS_BUCKETS
会输出 10 列,具体如下:语法元素 说明 db_name 数据库名 table_name 表名 partition_name 分区名 column_name 根据 is_index 来变化:is_index 为 0 时是列名,为 1 时是索引名 is_index 是否是索引列 bucket_id 桶的编号 count 所有落在这个桶及之前桶中值的数量 repeats 最大值出现的次数 lower_bound 最小值 upper_bound 最大值 删除统计信息
可以通过执行
DROP STATS
语句来删除统计信息。语法如下:
DROP STATS TableName;
该语句会删除 TableName 中所有的统计信息。
统计信息的导入导出
导出统计信息
统计信息的导出接口如下。
通过以下接口可以获取数据库
${db_name}
中的表${table_name}
的 json 格式的统计信息:http://${tidb-server-ip}:${tidb-server-status-port}/stats/dump/${db_name}/${table_name}
通过以下接口可以获取数据库
${db_name}
中的表${table_name}
在指定时间上的 json 格式统计信息。指定的时间应在 GC SafePoint 之后。http://${tidb-server-ip}:${tidb-server-status-port}/stats/dump/${db_name}/${table_name}/${yyyyMMddHHmmss}
通过以下接口可以获取数据库
${db_name}
中的表${table_name}
在指定时间上的 json 格式统计信息。指定的时间应在 GC SafePoint 之后。http://${tidb-server-ip}:${tidb-server-status-port}/stats/dump/${db_name}/${table_name}/${yyyy-MM-dd HH:mm:ss}
导入统计信息
导入的统计信息一般是通过统计信息导出接口得到的 json 文件。
语法如下:
LOAD STATS 'file_name';
file_name
为要导入的统计信息的文件名。另请参阅
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论