本文将为您介绍如何使用Analyze命令,以及更加简单的Auto Analyze的相关机制。

Analyze

统计信息决定是否能够生成正确的执行计划。Hologres需要收集数据的采样统计信息,包括数据的分布和特征、表的统计信息、列的统计信息、行数、列数、字段宽度、基数、频度、最大值、最小值、长键值、分桶分布特征等信息。这些信息将为优化器更新算子执行预估COST、搜索空间裁剪、估算最优JOIN ORDER、估算内存开销、估算并行度,从而生成更优的执行计划。

Analyze命令用于收集数据库中表内容的统计信息,优化器会根据这些统计信息生成最佳的查询计划,从而提高查询效率。
  • 使用语法
    -- 更新某个表的统计信息,默认会收集表中所有列的统计信息
    analyze <tablename>;
    
    -- 更新某个列的统计信息,会比更新表时采样的数据更多,更精准,主要用于更新管理条件的列
    analyze <tablename>(<colname>, <colname>);
  • 参数说明

    tablename为更新统计信息的表名称,colname为更新统计信息的列名称。

推荐您在如下情况下运行analyze <tablename>;命令。
  • 在表导入数据之后。
  • 在表执行大量的INSERT、UPDATE以及DELETE操作之后。
  • 内部表、外部表均需要ANALYZE。
  • 分区表针对父表做ANALYZE。
  • 如果遇到以下问题,您需要先执行analyze table,再运行导入任务,可以系统地提升效率。
    • 多表JOIN超出内存OOM:通常会产生Query executor exceeded total memory limitation xxxxx: yyyy bytes used报错。
    • 导入效率较低:在Hologres查询或导入数据时,效率较低,运行的任务长时间不结束。
表的统计信息被记录在hologres_statistic.hg_table_statistic表中,可以通过检查该信息了解Analyze的状态,命令如下。
SELECT schema_name, table_name, sample_rows, analyze_timestamp
FROM hologres_statistic.hg_table_statistic WHERE table_name='<tablename>';

Auto Analyze

从Hologres V0.10版本开始,将支持Auto Analyze机制,无需再手动对表进行Analyze。您可以通过命令语句开启Auto Analyze,系统会根据用户的数据写入、修改或者查询的情况来判断是否需要对相关的表自动进行Analyze,降低操作复杂度。

Auto Analyze使用限制

在Hologres中使用Auto Analyze,具体限制如下:
  • Auto Analyze功能仅Hologres V0.10及以上版本支持,请在Hologres管理控制台的实例详情页查看当前版本,如果您的实例是V0.10以下版本,请您提交工单升级实例。
  • 从HologresV1.1版本开始,默认开启Auto Analyze,V0.10版本默认不开启,需要执行命令开启。
  • 仅支持Superuser执行开启或关闭Auto Analyze操作。
  • 开启或关闭Auto Analyze的操作仅针对数据库级别生效,不针对单表。

开启Auto Analyze

您可以通过执行以下命令语句查看是否开启了Auto Analyze。
--V1.1版本命令语法
show hg_enable_start_auto_analyze_worker;

--V0.10版本命令语法
show hg_experimental_enable_start_auto_analyze_worker;
您可以通过执行以下命令语句开启Auto Analyze。
  • HologresV1.1版本将会默认开启Auto Analyze,若是已关闭,可以执行以下命令语句开启Auto Analyze。
    --DB级别,执行后整个DB生效,V1.1版本语法格式
    alter database <databasename> set hg_enable_start_auto_analyze_worker = on;
  • HologresV0.10版本默认不开启,可以通过以下命令语句开启Auto Analyze。
    --DB级别,执行后整个DB生效,V0.10版本语法格式
    alter database <databasename> set hg_experimental_enable_start_auto_analyze_worker = on;
以下几种情况会触发Auto Analyze机制,Superuser也可以根据业务情况更改默认参数,以此达到部分性能调优的目的。更多关于触发机制的说明和后台参数配置,请参见Auto Analyze配置参数
  • DML语句执行完成。
  • 新建一个表。
  • 外部表最后更新时间发生了改变,会触发外部表的Auto Analyze。
  • 后台默认设置检查机制进行Auto Analyze,具体机制如下:
    • 内部表默认每10分钟执行一次Auto Analyze。
    • 外部表默认每4小时执行一次Auto Analyze。
    • 扫描表的最大记录数是224条(16,777,216条),如果表的记录条数超过224条,将不再对超过的记录数自动进行Auto Analyze。
    • 表超过3天无Flink或Blink实时写入,则不会对表进行Auto Analyze。

关闭Auto Analyze

当您的业务不需要Auto Analyze时,例如查询的query比较固定,实例的Superuser可以通过如下命令语句关闭Auto Analyze。
--DB级别,执行后整个DB生效,V1.1及以上版本使用以下命令语法
alter database <databasename> set hg_enable_start_auto_analyze_worker = off;

--DB级别,执行后整个DB生效,V0.10版本使用以下命令语法
alter database <databasename> set hg_experimental_enable_start_auto_analyze_worker = off;

Auto Analyze配置参数

当您开启了Auto Analyze后,系统会根据默认设定的时间和机制进行巡检并执行Auto Analyze,会消耗一定的资源。在某些业务场景下,默认的机制可能会不适用业务场景,例如数据写入更新不频繁场景,可以通过修改默认参数来减少Auto Analyze的频率。

可以根据业务情况更改默认参数,以此达到部分性能调优的目的。

  • 命令语句alter database <databasename> set xxx 代表数据库级别,对整个数据库修改生效,需要Superuser执行。
  • 命令语句set xxx代表Session级别,需要和SQL一起执行,只对当前Session生效。
  • 参数默认时间单位为秒(s),使用默认单位时,单位s需要省略。
  • 在一些业务场景下,时间表示需要比较精细,且时间量级到达天级时也不好用秒来转换表示,Hologres针对这种业务场景对默认时间单位进行了“ms”、“s”、“min”、“h”和“dd”级的封装,使用这种带单位更精细的格式,需要给参数值上加上单引号,示例如下。
    --V1.1及以上版本命令语法
    set hg_auto_check_table_changes_interval = '10min';
    
    --V0.10版本命令语法
    set hg_experimental_auto_check_table_changes_interval = '10min';

Auto Analyze使用示例

  • 修改周期性检查所有内部表的更新时间间隔,内部表默认每10分钟执行一次Auto Analyze。
    • 参数单位为s时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_auto_check_table_changes_interval = 600;
      
      --V0.10版本命令语法
      set hg_experimental_auto_check_table_changes_interval = 600;
    • 参数单位为min时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_auto_check_table_changes_interval = '10min';
      
      --V0.10版本命令语法
      set hg_experimental_auto_check_table_changes_interval = '10min';
  • 修改周期性检查所有外表的更新时间间隔,外部表默认每4小时执行一次Auto Analyze。
    • 参数单位为s时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_auto_check_foreign_table_changes_interval = 14400;
      
      --V0.10版本命令语法
      set hg_experimental_auto_check_foreign_table_changes_interval = 14400;
    • 参数单位为min时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_auto_check_foreign_table_changes_interval = '4h';
      
      --V0.10版本命令语法
      set hg_experimental_auto_check_foreign_table_changes_interval = '4h';
    --session级别,只对当前连接生效。
    set hg_experimental_auto_check_foreign_table_changes_interval = '240min';
    
    --DB级别,执行后整个DB生效,将<databasename>替换为实际的DB名称。
    alter database <databasename> set hg_experimental_auto_check_foreign_table_changes_interval = '240min';
  • 修改Hologres内部表Flink或Blink写入的最大延迟,默认表超过3天无Flink或Blink实时写入,则不会对表进行Auto Analyze。
    • 参数单位为s时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_fixed_api_modify_max_delay_interval = 259200;
      
      --V0.10版本命令语法
      set hg_experimental_fixed_api_modify_max_delay_interval = 259200;
    • 参数单位为day时的使用示例如下。
      --V1.1及以上版本命令语法
      set hg_fixed_api_modify_max_delay_interval = '3day';
      
      --V0.10版本命令语法
      set hg_experimental_fixed_api_modify_max_delay_interval = '3day';
                                  
  • 修改扫描表的最大记录数,扫描表的最大记录数默认是224条(16,777,216条),如果表的记录条数超过224条,将不再对超过的记录数自动进行Auto Analyze。
    说明 对于分区表,224条是指整个父表的记录条数。
    --V1.1及以上版本命令语法
    set hg_auto_analyze_max_sample_row_count = 16777216;
    
    --V0.10版本命令语法
    set hg_experimental_auto_analyze_max_sample_row_count = 16777216;