すべてのプロダクト
Search
ドキュメントセンター

PolarDB:列ストアインデックスのクエリフィルタリングアルゴリズムの設定

最終更新日:Dec 14, 2025

クエリの実行中、列ストアインデックスのプルーナー機能は、アクセスする必要のないデータブロックをフィルタリングすることで、SQL クエリのパフォーマンスを向上させます。このトピックでは、プルーナーのシナリオ、考慮事項、構文、および関連パラメーターについて説明します。

概要

列ストアインデックスのデータは、単一列のデータブロックに格納され、デフォルトの粒度はブロックあたり 64,000 行です。データブロックの数は、テーブルの総行数 / 64000 という数式で見積もることができます。ある行セットのすべての列パックは、行グループを形成します。データスキャンでは、指定された列のすべてのデータブロックを走査して、フィルター条件を満たすレコードを取得する必要があります。大規模なテーブルをクエリする場合、スキャンのオーバーヘッドは高くなります。テーブルデータが完全にメモリに収まらない場合、オーバーヘッドはさらに増加します。実際には、統計情報と特定のフィルター条件を使用して、不要なデータブロックをスキップし、クエリを高速化できます。 PolarDB の列ストアインデックスでは、このメソッドはプルーナーと呼ばれます。現在、次の 4 種類のプルーナーがサポートされています。

  • ブルームフィルター

    • ビット配列を使用してセットを表し、要素がそのセットに属するかどうかを判断します。

    • プレフィックスブルームフィルター:文字列のプレフィックスに基づいてブルームフィルターを構築し、長い文字列によるパフォーマンスとストレージのオーバーヘッドを削減します。サポートされているバージョンは次のとおりです。

      • MySQL 8.0.1、リビジョンバージョン 8.0.1.1.42 以降。

      • MySQL 8.0.2、リビジョンバージョン 8.0.2.2.25 以降。

  • Min-Max インデックス

    各データブロックの最小値と最大値を格納します。フィルター条件をこれらの値と比較して、ブロックをスキャンするかどうかを決定します。

  • トークンブルームフィルター

    英数字以外の文字で文字列を分割してフィルタリングします。たとえば、「I am IMCI」は I |am|IMCI となります。これは LIKE あいまいクエリに適しています。

  • N-gram ブルームフィルター

    指定された長さの部分文字列に文字列を分割してフィルタリングします。たとえば、N-gram サイズが 3 の文字列「storage」は sto|tor|ora|rag|age となります。これは LIKE あいまいクエリに適しています。

シナリオ

  • ブルームフィルター:等価条件および IN 条件に最適です。文字列 ID でフィルタリングする場合など、等価条件の選択性が高い場合に強力なフィルタリングを提供します。

  • Min-Max インデックス:列データの局所性が高い場合に効果的で、特に日付やソートされたフィールドを含む WHERE 句などの範囲フィルターや等価フィルターに適しています。

  • トークンブルームフィルターと N-gram ブルームフィルターは、LIKE あいまいクエリで一致しないデータブロックを迅速に除外します。

ストレージのオーバーヘッド

文字列型の列に対してプルーナーを有効にすると、ストレージとメモリのオーバーヘッドが増加します。シナリオに応じて、ブルームフィルター、Min-Max インデックス、トークンブルームフィルター、N-gram ブルームフィルターなど、構築するプルーナーの種類を選択できます。メモリ使用量の数式は次のとおりです。

  • ブルームフィルタートークンブルームフィルター、または N-gram ブルームフィルター

    • デフォルトの 64,000 行のブロックサイズで、個別値の数が総行数の 3% を超える場合:

      メモリ使用量 = 1.2 × ブルームフィルターを持つ列数 × テーブルの総行数 (バイト)

    • デフォルトの 64,000 行のブロックサイズで、個別値の数が総行数の 3% 以下の場合:

      メモリ使用量 = 1.2 × ブルームフィルターを持つ列数 × 個別値の数 (バイト)

      この場合、ブルームフィルターの有効性はデータの局所性に依存します。データが均一に分散している場合、パフォーマンスは低下します。

  • Min-Max インデックス

    メモリ使用量の数式は次のとおりです。

    メモリ使用量 = 2 × Min-Max インデックスを持つ列数 × (テーブルの総行数 / ブロックサイズ) × プレフィックス長 × 文字コード長

    たとえば、20 億行のテーブルで、10 列に Min-Max インデックスがあり、プレフィックス長が 20、ブロックサイズが 64,000、文字コードが utf8mb4 (1 文字あたり 4 バイト) の場合、約 46 MB のメモリを使用します。

注意事項

  • PolarDB for MySQL バージョン 8.0.1.1.32 以前、または 8.0.2.2.13 以前を実行するクラスターでは、NULL 値を含むデータブロックに対してプルーナーは構築されません。IS NULL または IS NOT NULL でのフィルタリングはサポートされていません。

  • PolarDB for MySQL バージョン 8.0.1.1.35 以降、または 8.0.2.2.16 以降を実行するクラスターでは、列ストアインデックスを作成する際に、文字列型の列に対してプルーナーが自動的に構築されます。ブルームフィルターは、メモリ管理に Least Recently Used (LRU) キャッシュを使用します。古いバージョンからアップグレードする場合、文字列型の列に対してプルーナーを有効にするには、列ストアインデックスを再構築する必要があります。

  • PolarDB for MySQL バージョン 8.0.1.1.34 以前、または 8.0.2.2.15 以前を実行するクラスターでは、プルーナーは永続的にメモリに残ります。列ストアインデックスの作成中に、文字列型の列に対してプルーナーは自動的に構築されません。

  • 文字列型の列に対してプルーナーを構築するには、文字列に「\0」が含まれていないことを確認する必要があります (例:「polar\0db」)。

  • システムは、INT、DECIMAL、DATETIME などの数値型に対して自動的に Min-Max インデックスを構築します。

  • Min-Max インデックスは、JSON または GEOMETRY フィールドではサポートされていません。

  • ブルームフィルターは、INT、DECIMAL、DATETIME などの数値型、または JSON、BLOB、TEXT フィールドではサポートされていません。

構文リファレンス

テーブルの作成時にプルーナーを構築したり、既存のテーブルに追加または削除したりできます。既存のテーブルのプルーナーを変更するには、まず列ストアインデックスを削除してから再作成する必要があります。構文は次のとおりです。

説明
  • データ定義言語 (DDL) 文を使用して、テーブルスキーマの COMMENT 属性を変更し、文字列型の列にプルーナーを追加または削除できます。

  • 列レベルの COMMENT 属性は、テーブルレベルの COMMENT 属性よりも優先されます。

  • 新しいバージョンでは、より多くのプルーナータイプがサポートされ、文字列に対する Min-Max インデックスやブルームフィルターなど、一般的なものがデフォルトで有効になっています。新しいプルーナーを追加する前に、各列の既存のプルーナータイプを確認してください。詳細については、「テーブル列にプルーナーが構築されているかどうかの確認」をご参照ください。

テーブル作成時のプルーナーの構築

  • プルーナー (ブルームフィルター) の構築

    説明

    PolarDB for MySQL 8.0、リビジョン 8.0.1.1.32 以降、または 8.0.2.2.13 以降を実行するクラスターは、PRUNER_BLOOM 属性をサポートしています。

    • サポートされているすべての列にブルームフィルターを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10),
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1 PRUNER_BLOOM=1"; /* コメント内の pruner_bloom 属性 */
    • 特定の列にブルームフィルターを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10) "PRUNER_BLOOM=1", /* コメント内の pruner_bloom 属性 */
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1";
  • プルーナー (minmax インデックス) の構築

    長い文字列の列の場合、システムは文字列のプレフィックスを最小値と最大値と比較して、メモリ使用量を削減します。デフォルトのプレフィックス長は 20 文字で、最大は 255 です。`PRUNER_MINMAX` を使用して文字列の Min-Max インデックスを有効にし、`PREFIX_LEN` を使用してプレフィックス長を設定できます。

    説明
    • 文字数は、エンコーディングの長さではなく、文字数に基づいています。たとえば、「Alibaba Cloud PolarDB」の最初の 2 文字は「Al」、最初の 5 文字は「Aliba」です。

    • PolarDB for MySQL 8.0、リビジョン 8.0.1.1.32 以降、または 8.0.2.2.13 以降を実行するクラスターは、PRUNER_MINMAX および PREFIX_LEN 属性をサポートしています。

    • すべての文字列の列に Min-Max インデックスを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10),
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1 PRUNER_MINMAX=1 PREFIX_LEN=30"; /* 30 文字のプレフィックスを持つ pruner_minmax 属性 */
    • 特定の列に Min-Max インデックスを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10) "PRUNER_MINMAX=1 PREFIX_LEN=30", /* 30 文字のプレフィックスを持つ pruner_minmax */
          str_col2 varchar(10) "PRUNER_MINMAX=1 PREFIX_LEN=10" /* 10 文字のプレフィックスを持つ pruner_minmax */
        ) ENGINE InnoDB COMMENT "COLUMNAR=1";
  • プレフィックスブルームフィルターの構築

    説明

    PolarDB for MySQL 8.0、リビジョン 8.0.1.1.42 以降、または 8.0.2.2.25 以降を実行するクラスターは、PRUNER_PREFIX_BLOOM 属性をサポートしています。

    • サポートされているすべての列にプレフィックスブルームフィルターを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10),
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1 PRUNER_PREFIX_BLOOM=1"; /* テーブルコメント内の PRUNER_PREFIX_BLOOM */
    • 特定の列にプレフィックスブルームフィルターを構築します。例:CREATE TABLE t1 ( id INT PRIMARY KEY, str_col1 char(10) "PRUNER_PREFIX_BLOOM=1", /* 列コメント内の PRUNER_PREFIX_BLOOM */ str_col2 varchar(10) ) ENGINE InnoDB COMMENT "COLUMNAR=1";

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10) "PRUNER_PREFIX_BLOOM=1", /* 列コメント内の PRUNER_PREFIX_BLOOM */
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1";
  • トークンブルームフィルターの構築

    説明

    PRUNER_TOKEN_BLOOM 属性は、次のバージョンでサポートされています。

    • PolarDB for MySQL 8.0.1、リビジョン 8.0.1.1.39 以降。

    • PolarDB for MySQL 8.0.2、リビジョン 8.0.2.2.20 以降。

    • サポートされているすべての列にトークンブルームフィルターを構築できます。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10),
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1 PRUNER_TOKEN_BLOOM=1";
    • 特定の列にトークンブルームフィルターを構築できます。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10) "PRUNER_TOKEN_BLOOM=1",
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1";
  • N-gram ブルームフィルターの構築

    説明
    • PRUNER_TOKEN_BLOOM プロパティは、次の条件を満たすクラスターバージョンでサポートされています。

      • PolarDB for MySQL 8.0.1、リビジョン 8.0.1.1.39 以降。

      • PolarDB for MySQL 8.0.2、リビジョン 8.0.2.2.20 以降。

    • PRUNER_NGRAM_BLOOM=N:N は 2 以上でなければならず、部分文字列の長さを設定します。N は LIKE "%string%" の文字列の長さ以下の値に設定することを推奨します。LIKE "%string%" の文字列が N より短い場合、N-gram ブルームフィルターは使用できません。

    • サポートされているすべての列に N-gram ブルームフィルターを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10),
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1 PRUNER_NGRAM_BLOOM=2";
    • 特定の列に N-gram ブルームフィルターを構築します。例:

      CREATE TABLE
        t1 (
          id INT PRIMARY KEY,
          str_col1 char(10) "PRUNER_NGRAM_BLOOM=3",
          str_col2 varchar(10)
        ) ENGINE InnoDB COMMENT "COLUMNAR=1";

既存のテーブルでのプルーナーの構築または削除

既存のテーブルにプルーナーを追加または削除するには、まず列ストアインデックスを削除してから再作成して、インデックスを再構築する必要があります。インデックスを再構築する前に、COMMENT のプルーナー属性を更新または削除します。次のセクションでは、PRUNER_MINMAX を例として使用します。

  • プルーナーを構築する

    元のテーブル構造が次のようになっていると仮定します。

           Table: t1
    Create Table: CREATE TABLE `t1` (
      `id` int(11) NOT NULL,
      `str_col1` char(10) DEFAULT NULL,
      `str_col2` varchar(10) DEFAULT NULL,
      PRIMARY KEY (`id`),
      COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1'
    • テーブル t1 のすべての文字列の列に Min-Max プルーナーを構築します。

      1. テーブル t1 の列ストアインデックスを削除します。

        ALTER TABLE t1 COMMENT = "COLUMNAR=0";
      2. テーブル t1 のすべての文字列の列に対して Min-Max プルーナーを有効にします。

        ALTER TABLE t1 COMMENT = "COLUMNAR=1 PRUNER_MINMAX=1"; 
      3. (任意) 更新されたテーブル構造を表示します。

        SHOW CREATE TABLE t1 FULL \G

        結果:

        *************************** 1. row ***************************
               Table: t1
        Create Table: CREATE TABLE `t1` (
          `id` int(11) NOT NULL,
          `str_col1` char(10) DEFAULT NULL,
          `str_col2` varchar(10) DEFAULT NULL,
          PRIMARY KEY (`id`),
          COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
        ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1 PRUNER_MINMAX=1'

        t1 テーブルに PRUNER_MINMAX 属性が含まれるようになりました。

    • テーブル t1str_col1 列に Min-Max プルーナーを構築します。

      1. str_col1 列にプルーナーを追加します。

        ALTER TABLE t1 MODIFY COLUMN str_col1 char(10) COMMENT 'PRUNER_MINMAX=1';
      2. 次のコマンドを順に実行して、テーブル t1 の列ストアインデックスを再構築します。

        ALTER TABLE t1 COMMENT = "COLUMNAR=0";
        ALTER TABLE t1 COMMENT = "COLUMNAR=1";
      3. (任意) 更新されたテーブル構造を表示します。

        SHOW CREATE TABLE t1 FULL \G

        結果:

        *************************** 1. row ***************************
               Table: t1
        Create Table: CREATE TABLE `t1` (
          `id` int(11) NOT NULL,
          `str_col1` char(10) DEFAULT NULL COMMENT 'PRUNER_MINMAX=1',
          `str_col2` varchar(10) DEFAULT NULL,
          PRIMARY KEY (`id`),
          COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
        ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1'

        str_col1 列に PRUNER_MINMAX 属性が追加されました。

  • プルーナーの削除

    • テーブルから PRUNER_MINMAX 属性を削除します。

      テーブル t1 が次の構造を持っていると仮定します。

      SHOW CREATE TABLE t1 full \G
      *************************** 1. row ***************************
             Table: t1
      Create Table: CREATE TABLE `t1` (
        `id` int(11) NOT NULL,
        `str_col1` char(10) DEFAULT NULL,
        `str_col2` varchar(10) DEFAULT NULL,
        PRIMARY KEY (`id`),
        COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
      ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1 PRUNER_MINMAX=1'

      テーブル t1 から PRUNER_MINMAX 属性を削除するには:

      1. 次のコマンドを実行して、テーブル t1 の列ストアインデックスを削除します。

        ALTER TABLE t1 COMMENT = "COLUMNAR=0";
      2. PRUNER_MINMAX を 0 に設定し、インデックスを再構築します。

        ALTER TABLE t1 COMMENT = "COLUMNAR=1 PRUNER_MINMAX=0";
      3. (任意) 更新されたテーブル構造を表示します。

        SHOW CREATE TABLE t1 FULL \G

        結果:

        *************************** 1. row ***************************
               Table: t1
        Create Table: CREATE TABLE `t1` (
          `id` int(11) NOT NULL,
          `str_col1` char(10) DEFAULT NULL,
          `str_col2` varchar(10) DEFAULT NULL,
          PRIMARY KEY (`id`),
          COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
        ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1'

        t1 テーブルには PRUNER_MINMAX 属性がなくなりました。

    • 列から PRUNER 属性を削除します。

      テーブル t1str_col1 列に PRUNER_MINMAX 属性があると仮定します。テーブル構造は次のとおりです。

             Table: t1
      Create Table: CREATE TABLE `t1` (
        `id` int(11) NOT NULL,
        `str_col1` char(10) DEFAULT NULL COMMENT 'PRUNER_MINMAX=1',
        `str_col2` varchar(10) DEFAULT NULL,
        PRIMARY KEY (`id`),
        COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
      ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1'

      str_col1 列から PRUNER_MINMAX 属性を削除するには:

      1. str_col1 列から PRUNER_MINMAX 属性を削除します。

        ALTER TABLE t1 MODIFY COLUMN str_col1 char(10) COMMENT 'PRUNER_MINMAX=0';
      2. 列ストアインデックスを再構築します。

        ALTER TABLE t1 COMMENT = "COLUMNAR=0";
        ALTER TABLE t1 COMMENT = "COLUMNAR=1";
      3. (任意) 更新されたテーブル構造を表示します。

        SHOW CREATE TABLE t1 FULL \G

        結果:

        *************************** 1. row ***************************
               Table: t1
        Create Table: CREATE TABLE `t1` (
          `id` int(11) NOT NULL,
          `str_col1` char(10) DEFAULT NULL,
          `str_col2` varchar(10) DEFAULT NULL,
          PRIMARY KEY (`id`),
          COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
        ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1'

        str_col1 列には PRUNER_MINMAX 属性がなくなりました。

テーブル列にプルーナーが構築されているかどうかの確認

バージョン 8.0.1.1.42 以降、または 8.0.2.2.25 以降

information_schema.imci_secondary_indexes テーブルを確認できます。INDEX_TYPE フィールドには、文字列の列のプルーナータイプが表示されます。プルーナーが存在する場合、そのタイプがこのフィールドに表示されます。

説明

バージョン 8.0.1.1.42 以降、または 8.0.2.2.25 以降では、information_schema.imci_secondary_indexes テーブルはより多くのフィールドで強化されています。

SELECT * FROM information_schema.imci_secondary_indexes \G
*************************** 1. row ***************************
         TABLE_ID: 1111
      SCHEMA_NAME: test_imci
       TABLE_NAME: lineitem
      COLUMN_NAME: l_returnflag -- 列名
       INDEX_TYPE: MinMax,PrefixBloom -- プルーナータイプ:Min-Max およびプレフィックスブルームフィルター
  MINMAX_RE_PACKS: 0 -- Min-Max プルーナーによってスキップされた累積パック数
  MINMAX_AC_PACKS: 0 -- 受け入れられた累積パック数 (すべてのレコードが一致し、行ごとの述語は不要)
MINMAX_TEST_PACKS: 0 -- Min-Max プルーナーの累積評価回数
   BLOOM_RE_PACKS: 0 -- ブルームフィルターによってスキップされた累積パック数
 BLOOM_TEST_PACKS: 0 -- ブルームフィルターの累積評価回数

バージョン 8.0.1.1.42 または 8.0.2.2.25 より前

information_schema.imci_secondary_indexes テーブルを確認できます。STR_BLOOM_PRUNER および STR_MINMAX_PRUNER フィールドは、プルーナーのステータスを示します。値が 1 の場合は、プルーナーが構築されていることを示します。

SELECT * FROM information_schema.imci_secondary_indexes WHERE schema_name='test_tmp' AND table_name='t1'\G
*************************** 1. row ***************************
         TABLE_ID: 1091
      SCHEMA_NAME: test_tmp
       TABLE_NAME: t1
      COLUMN_NAME: str_col1
 STR_BLOOM_PRUNER: 1 -- str_col1 用に構築されたブルームフィルター
STR_MINMAX_PRUNER: 1 -- str_col1 用に構築された Min-Max
    SINDEX_SWITCH: 0
*************************** 2. row ***************************
         TABLE_ID: 1091
      SCHEMA_NAME: test_tmp
       TABLE_NAME: t1
      COLUMN_NAME: str_col2
 STR_BLOOM_PRUNER: 1 -- str_col2 用に構築されたブルームフィルター
STR_MINMAX_PRUNER: 1 -- str_col2 用に構築された Min-Max
    SINDEX_SWITCH: 0

クエリ結果は、STR_BLOOM_PRUNER フィールドのステータス値が 1 であることは、str_col1 および str_col2 に対してブルームフィルターが構築されていることを示します。STR_MINMAX_PRUNER フィールドのステータス値が 1 であることは、str_col1 および str_col2 に対して Min-Max インデックスが構築されていることを示します

プルーナーの有効性の検証

SHOW STATUS を使用した確認

クエリを実行する前後に、SHOW STATUS LIKE 'imci_pruner%' を使用してデータブロックのフィルタリングを検査し、プルーナーの効果を確認できます。これらの値は、現在のセッションの累積プルーナーメトリックです。複数テーブルのクエリの場合、結果はすべてのテーブルで合計されます。ステータス値は次のように説明されます。

  • imci_pruner_accepted:フィルター条件を完全に満たすデータブロックの数。

  • imci_pruner_rejected:フィルター条件を満たさないデータブロックの数。

スキップされたブロックの合計数は、受け入れられたブロックと拒否されたブロックの合計です。

受け入れられたブロックはレコードごとのフィルタリングをスキップしますが、マテリアライズにはアクセスが必要な場合があります。拒否されたブロックはスキャンプロセス全体をスキップし、I/O は発生しません。

テーブル t1 を例として、検索文に対してプルーナーが有効かどうかを判断します。テーブル t1 のテーブルスキーマは次のとおりです。

       Table: t1
Create Table: CREATE TABLE `t1` (
  `id` int(11) NOT NULL,
  `str_col1` char(10) DEFAULT NULL,
  `str_col2` varchar(10) DEFAULT NULL,
  PRIMARY KEY (`id`),
  COLUMNAR INDEX (`id`,`str_col1`,`str_col2`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci COMMENT='COLUMNAR=1 PRUNER=1'

テーブルに 10 個のデータブロックが含まれており、条件 str_col1='polardb' を満たすレコードが単一のデータブロックに集中していると仮定します。次の手順を実行して、SELECT COUNT(1) FROM t1 WHERE str_col1='polardb' 検索文でプルーナーが有効になるかどうかを確認できます。

  1. 現在のプルーナーのステータスを確認します。

    SHOW STATUS LIKE  'imci_pruner%';

    結果:

    +----------------------+-------+
    | Variable_name        | Value |
    +----------------------+-------+
    | imci_pruner_accepted | 0     |
    | imci_pruner_rejected | 0     |
    +----------------------+-------+
    2 rows in set (0.00 sec)
  2. 次のコマンドを実行して、条件 str_col1='polardb' を満たす行数をクエリします。

    SELECT COUNT(1) FROM t1 WHERE str_col1='polardb';

    結果:

    +----------+
    | count(1) |
    +----------+
    |        1 |
    +----------+
    1 row in set (0.01 sec)
  3. プルーナーのステータスを再度確認します。

    SHOW STATUS LIKE  'imci_pruner%';

    結果:

    +----------------------+-------+
    | Variable_name        | Value |
    +----------------------+-------+
    | imci_pruner_accepted | 0     |
    | imci_pruner_rejected | 9     |
    +----------------------+-------+
    2 rows in set (0.00 sec)

    imci_pruner_accepted の値は 0、imci_pruner_rejected の値は 9 です。クエリは 9 つのブロックをスキップしたため、プルーナーの有効性が確認されます。

imci_sql_profiling を使用した確認

説明

この機能は、PolarDB for MySQL 8.0、リビジョン 8.0.1.1.5 以降、または 8.0.2.2.29 以降でのみサポートされています。

information_schema.imci_sql_profiling をクエリして、実行計画で Table Scan オペレーターがプルーナーを使用してフィルタリングしたデータパケットの数を確認できます。SHOW STATUS での確認とは異なり、このメソッドはクエリに直接関連付けられたテーブルレベルのフィルタリングを示します。SHOW STATUS コマンドはセッションスコープであり、手動での差分計算が必要です。したがって、このメソッドの方が直感的です。

  1. 列ストアインデックスのクエリプロファイリングを有効にします。

    SET imci_analyze_query=ON;
  2. クエリを実行します。例:

    SELECT count(*) from t1 WHERE v1 > 100;
    +--------------+
    | count(*)     |
    +--------------+
    | 600          |
    +--------------+
  3. imci_sql_profiling テーブルを確認します。

    SELECT `Operator`, `Extra Info` from INFORMATION_SCHEMA.IMCI_SQL_PROFILING;
    +----+------------------------------------------------------------------------------+-----------------------------------------------------------------------------------------------------------+
    | ID | Operator                                                                     | Extra Info                                                                                                |
    +----+------------------------------------------------------------------------------+-----------------------------------------------------------------------------------------------------------+
    |  1 | Select Statement                                                             | IMCI Execution Plan (max_dop = 32, real_dop = 32, max_query_mem = unlimited, real_query_mem = unlimited)  |
    |  2 | └─Aggregation                                                                |                                                                                                           |
    |  3 |   └─Table Scan	Cond: (v1 > 100), Pruner Counter: [AC: 8, RE: 1, PA: 2]     |                                                                                                           |
    +----+------------------------+-----------------------------------------------------------------------------------------------------------------------------------------------------------------+

    AC: 8 は 8 つのパケットが受け入れられたことを示します。RE: 1 は 1 つのパケットが拒否されたことを示します。PA: 2 は 2 つのパケットが部分的に一致し、さらなるフィルタリングが必要であったことを示します。

Performance Testing

このセクションでは、2 コア、4 GB のクラスターで、約 1,800 のデータブロックに相当する 1 億 2,000 万行のテーブルでのテストについて説明します。文字列の列 col には 8,000 万の個別値があります。このテストでは、次のステートメントを使用して、ブルームフィルターの有無によるクエリパフォーマンスを比較します。

SELECT COUNT(1) FROM t1 WHERE col='xxx'

クエリ時間は次のとおりです。

ブルームフィルターの構築

ブルームフィルターなし

0.15 秒

18.6 秒

条件 col='xxx' とブルームフィルターを組み合わせることで、ほとんどのデータブロックが除外されました。スキャンされたのはごく少数のブロックのみで、パフォーマンスが大幅に向上しました。