Redrock Postgres 搜索 英文
版本: 9.3 / 9.4 / 9.5 / 9.6 / 10 / 11 / 12 / 13 / 14 / 15 / 16

ANALYZE

名称

ANALYZE -- 收集有关一个数据库的统计信息

大纲

ANALYZE [ VERBOSE ] [ table_name [ ( column_name [, ...] ) ] ]

描述

ANALYZE收集一个数据库中的表的内容的 统计信息,并且将结果存储在pg_statistic 系统目录中。接下来,查询规划器会使用这些统计信息来帮助确定查询 最有效的执行计划。

如果不带参数,ANALYZE会检查当前 数据库中的所有表。如果带有一个参数, ANALYZE只会检查那个表。可以进一 步给出一个列名的列表,该情况下只会收集这些列的统计信息。

参数

VERBOSE

允许显示进度消息。

table_name

要分析的一个指定表的名称(可以是模式限定的)。如果省略,当前 数据库中所有常规表(非外部表)都会被分析。

column_name

要分析的一个指定列的名称。默认是所有列。

输出

当指定了VERBOSE时,ANALYZE 会发出进度消息来指示当前正在处理哪个表。还会打印有关那些表 的多种统计信息。

注解

只有被显式选中时才会分析外部表。并非所有外部数据包装器都支持 ANALYZE。如果表的包装器不支持 ANALYZE,该命令会打印一个警告并且什么也不做。

在默认的PostgreSQL配置中, 自动清理守护进程(见第 23.1.6 节)会在表第一 次载入数据或者用常规操作改变时负责表的自动分析。当启用自动清理 时,定期运行ANALYZE是个好主意,或者 可以在表内容做了大的修改后运行ANALYZE。 准确的统计信息将帮助规划器选择最合适的查询计划,从而提升查询处理 的速度。主读数据库的一般策略是在一天中使用量最低时运行一次 VACUUMANALYZE (如果有大量的更新动作则是不够的)。

ANALYZE只要求目标表上的一个读锁,因此 它可以和表上的其他动作并行。

ANALYZE收集的统计信息通畅包括每列中最常见 值的列表以及展示每列中近似数据分布的一个直方图。如果 ANALYZE认为这些东西无趣(例如在一个唯一键 列中,没有共同值)或者该列的数据类型不支持合适的操作符,以上工作都会被 省略。在第 23 章中有与统计信息相关的更多信息。

对于大型的表,ANALYZE会对表内容做 随机采样而不是检查每一行。这允许在很少的时间内完成对大型表的 分析。不过要注意,这些统计信息只是近似值,并且即使实际表内容没 有改变,每次运行ANALYZE时统计信息 都会有微小地改变。这可能会导致EXPLAIN显示 的规划器估算代价有小的改变。在很少的情况下,这会非决定性地导致 规划器的查询计划选择在ANALYZE运行后 改变。为了避免这种情况,可以按照下文所述提高 ANALYZE所收集的统计信息量。

The extent of analysis can be controlled by adjusting the 通过调整default_statistics_target配置变量可以 控制分析量,对每个列可以用 ALTER TABLE ... ALTER COLUMN ... SET STATISTICS设置每列的统计信息目标(见 ALTER TABLE)。目标值会设置最常用值列表中的最大 项数以及直方图中的最大容器数。默认目标值是 100,可以把它调大或者调 小在规划器估计值精度和ANALYZE花费的时间 以及pg_statistic所占空间之间做出平衡。特别地,将统 计信息目标设置为零会禁用该列的统计信息收集。在查询的 WHEREGROUP BY或者 ORDER BY子句中从不出现的列上这样做会有所帮助,因为 规划器用不上这些列上的统计信息。

被分析的列中最大的统计信息目标决定了为准备统计信息要采样的表行数。 增加该目标会导致做ANALYZE所需的时间和 空间成比例增加。

ANALYZE所估算的值之一是出现在每个列中 的可区分值。因为只会检查行的一个子集,即便使用最大的统计信息目标, 这种估计有时也可能很不精确。如果这种不精确导致不好的查询计划,可以 手工确定一个更精确的值并且用 ALTER TABLE ... ALTER COLUMN ... SET (n_distinct = ...) 设置该值(见ALTER TABLE)。

如果被分析的表有一个或者更多子女, ANALYZE将会收集两次统计信息:一次只对 父表的行收集,第二次则在父表及其所有子女表的行上收集。在规划需要 遍历整个继承树的查询时需要第二个统计信息集。不过,在决定是否触发表 上的自动分析时,自动清理后台进程将只考虑父表本身上的插入和更新。如 果该表很少被插入或者更新,只有手工运行 ANALYZE时才会把继承统计信息更新到最新。

如果任何子表是外部表并且其外部数据封装器不支持ANALYZE, 在收集继承统计信息时会忽略那些子表。

如果被分析的表不完全为空,ANALYZE 将不会为该表记录新统计信息。任何现有统计信息将会被保留。

兼容性

SQL 标准中没有ANALYZE语句。

另见

VACUUM, vacuumdb, 第 18.4.4 节, 第 23.1.6 节