OceanBase logo

OceanBase

トランザクション処理、分析、AIワークロードに最適な分散データベース

デプロイを自由に

OceanBase Cloud

OceanBaseの導入とスケーリングを最適化

エンタープライズ版

自社インフラ上での運用・管理に対応

オープンソース版を試す

コミュニティ版

開発者向けオープンソース分散データベース

OceanBase seekdb

AIネイティブなオープンソースの検索データベース

顧客事例

さまざまな業界の企業による導入事例を紹介します。

さらに見る
利用シーン別

あらゆるシナリオに対応するOLTP

ハイブリッドクラウドソリューション

大容量ストレージデータベースのコスト削減

リアルタイム分析混合ワークロード

複数インスタンスの統合

ドキュメント

会社概要

OceanBaseの企業情報、パートナーシップ、そして信頼性・セキュリティへの取り組みについて紹介します。

OceanBaseについて

法的情報

お問い合わせ

日本 - 日本語
International - English
中国站 - 简体中文
クラウドで始める

トランザクション処理、分析、AIワークロードに最適な分散データベース

デプロイを自由に

OceanBase Cloud

OceanBaseの導入とスケーリングを最適化

エンタープライズ版

自社インフラ上での運用・管理に対応

オープンソース版を試す

コミュニティ版

開発者向けオープンソース分散データベース

OceanBase seekdb

AIネイティブなオープンソースの検索データベース

顧客事例

さまざまな業界の企業による導入事例を紹介します。

さらに見る
利用シーン別

あらゆるシナリオに対応するOLTP

ハイブリッドクラウドソリューション

大容量ストレージデータベースのコスト削減

リアルタイム分析混合ワークロード

複数インスタンスの統合

OceanBaseの企業情報、パートナーシップ、そして信頼性・セキュリティへの取り組みについて紹介します。

OceanBaseについて

法的情報

お問い合わせ

クラウドで始める
编组
すべての製品
    • データベース
    • アイコンOceanBaseデータベース
アイコン

OceanBaseデータベース

V4.3.5

    OceanBase logo

    AI時代を支える分散データベース

    日本 - 日本語
    International - English
    中国站 - 简体中文
    プロダクト
    OceanBase Cloudエンタープライズ版コミュニティ版OceanBase seekdb
    会社概要
    OceanBaseについて法的情報お問い合わせ
    公式アカウント
    ConnpassXQiitaLumaGitHub

    © OceanBase 2026. All rights reserved

    クラウドサービス契約個人情報保護ポリシーセキュリティ
    お問い合わせ
    ドキュメントフィードバック
    1. ホーム
    2. OceanBaseデータベース
    3. V4.3.5
    アイコンOceanBaseデータベース
    V 4.3.5
    • V 4.3.5

    TABLE SCAN

    最終更新日:2026-04-09 08:28:49  更新
    シェア
    このページの内容
    シェア

    TABLE SCAN 演算子はストレージ層とSQL層のインターフェースであり、オプティマイザーがどのインデックスを使用してデータにアクセスするかを示すために使用されます。

    OceanBaseデータベースV4.1.0バージョンでは、通常のインデックスとグローバルインデックスについて、インデックスからテーブルへのロードのロジックは TABLE SCAN 演算子にカプセル化されています。実行計画を表示する際には、is_index_back が演算子がテーブルへのロードを必要とするかどうかを示し、is_global_index が演算子がグローバルインデックスをスキャンするかどうかを示します。 例:TABLE SCAN 演算子を含む実行計画

    Q1:
    obclient> CREATE TABLE t1(c1 INT PRIMARY KEY, c2 INT, c3 INT, c4 INT);
    obclient> CREATE INDEX e1 ON t1(c1,c2);
    obclient> EXPLAIN SELECT * FROM t1 WHERE c1 = 1;
    +--------------------------------------------------------------------------+
    | Query Plan                                                               |
    +--------------------------------------------------------------------------+
    | =========================================                                |
    | |ID|OPERATOR |NAME|EST.ROWS|EST.TIME(us)|                                |
    | -----------------------------------------                                |
    | |0 |TABLE GET|T1  |1       |3           |                                |
    | =========================================                                |
    | Outputs & filters:                                                       |
    | -------------------------------------                                    |
    |   0 - output([T1.C1], [T1.C2], [T1.C3], [T1.C4]), filter(nil), rowset=16 |
    |       access([T1.C1], [T1.C2], [T1.C3], [T1.C4]), partitions(p0)         |
    |       is_index_back=false, is_global_index=false,                        |
    |       range_key([T1.C1]), range[1 ; 1],                                  |
    |       range_cond([T1.C1 = 1])                                            |
    +--------------------------------------------------------------------------+
    

    上記の例では、実行計画表示の outputs & filters において、TABLE SCAN 演算子の出力情報を以下のように詳細に示しています:

    情報名 意味
    operator TABLE SCAN 演算子の operator には3つの形式があります:TABLE SCAN、TABLE GET、TABLE SKIP SCAN。
    • TABLE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    • TABLE GET は主キーを直接使用して位置特定し、0行または1行のデータを返します。
    • TABLE SKIP SCAN は範囲スキャンに属し、ジャンプ実行で、0行または複数行のデータを返します。
    name データにアクセスするために使用するインデックスを選択します。選択したインデックスの名前はテーブル名の後に続きます。インデックス名がない場合は、主表スキャンが実行されていることを意味します。ここで注意すべき点は、OceanBaseデータベースでは、主表とインデックスの組織構造が同じであり、主表自体もインデックスであるということです。
    output この演算子の出力列。
    filter この演算子のフィルター述語。例のQ1クエリでは、TABLE GET 演算子に filter が設定されていないため、nil となります。
    partitions スキャンするパーティションを指定します。
    is_index_back この演算子がテーブルへのアクセスを必要とするかどうかを示します。例えば、Q1クエリでは主表が選択されているため、テーブルへのアクセスは不要です。
    is_global_index この演算子がグローバルインデックスをスキャンするかどうかを示します。例えば、Q2クエリでは通常のインデックスが使用されているため、is_global_index は false です。Q3クエリでは、t2 テーブルの i2 インデックスが使用されており、i2 インデックスはグローバルインデックスであるため、is_global_index は true です。
    range_key/range/range_cond
    • range_key:インデックスの rowkey 列。
    • range:インデックスのスキャン開始位置と終了位置。フルテーブルスキャンかどうかを判断するには、range の範囲に注目する必要があります。例えば、rowkey が3列ある場合、range(MIN,MIN, MIN ; MAX, MAX, MAX) は真の意味でのフルテーブルスキャンを表します。
    • range_cond:インデックスのスキャン開始位置と終了位置を決定する関連述語。
    Q2:
    obclient> CREATE INDEX e1 ON t1(c2,c3);
    obclient> EXPLAIN SELECT * FROM t1 WHERE c2 < 1 AND c3 < 1 AND c4 < 1;
    +---------------------------------------------------------------------------------------------------------------------------------------------+
    | Query Plan                                                                                                                                  |
    +---------------------------------------------------------------------------------------------------------------------------------------------+
    | ==================================================                                                                                          |
    | |ID|OPERATOR        |NAME  |EST.ROWS|EST.TIME(us)|                                                                                          |
    | --------------------------------------------------                                                                                          |
    | |0 |TABLE RANGE SCAN|T1(E1)|1       |5           |                                                                                          |
    | ==================================================                                                                                          |
    | Outputs & filters:                                                                                                                          |
    | -------------------------------------                                                                                                       |
    |   0 - output([T1.C1], [T1.C2], [T1.C3], [T1.C4]), filter([T1.C3 < cast(1, NUMBER(-1, -85))], [T1.C4 < cast(1, NUMBER(-1, -85))]), rowset=16 |
    |       access([T1.C1], [T1.C2], [T1.C3], [T1.C4]), partitions(p0)                                                                            |
    |       is_index_back=true, is_global_index=false, filter_before_indexback[true,false],                                                       |
    |       range_key([T1.C2], [T1.C3], [T1.C1]), range(MIN,MIN,MIN ; 1,MIN,MIN),                                                                 |
    |       range_cond([T1.C2 < cast(1, NUMBER(-1, -85))])                                                                                        |
    +---------------------------------------------------------------------------------------------------------------------------------------------+
    12 rows in set
    

    上記の例では、実行計画表示の outputs & filters において、TABLE SCAN 演算子の出力情報を以下のように詳細に示しています:

    情報名 意味
    operator TABLE SCAN 演算子の operator には3つの形式があります:TABLE SCAN、TABLE GET、TABLE SKIP SCAN。
    • TABLE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    • TABLE GET は主キーを直接使用して位置特定し、0行または1行のデータを返します。
    • TABLE SKIP SCAN は範囲スキャンに属し、ジャンプ実行され、0行または複数行のデータを返します。
    Q2のクエリでは、TABLE RANGE SCAN はRANGE条件でテーブルからデータを検索する操作を表します。
    name データにアクセスするために使用するインデックスを選択します。選択したインデックスの名前はテーブル名の後に続きます。インデックスの名前がない場合、主表スキャンが実行されていることを意味します。ここで注意すべき点は、OceanBaseデータベースでは、主表とインデックスの組織構造が同じであり、主表自体もインデックスであるということです。
    output この演算子の出力列。
    filter この演算子のフィルター述語。例えば、Q2のクエリでは、filter([T1.C2 < 1], [T1.C3 < 1], [T1.C4 < 1]) は、テーブルT1の全表スキャン結果に対して3つのフィルター条件を適用したことを示します。それぞれ、C2列の値が1未満、C3列の値が1未満、およびC4列の値が1未満です。クエリ実行時にこれらの条件を満たす行は、最終結果セットに含まれます。
    partitions スキャンするパーティションを指定します。
    is_index_back この演算子がテーブルへのアクセスを必要とするかどうかを示します。 例えば、Q1のクエリでは、主表が選択されているため、テーブルへのアクセスは不要です。Q2のクエリでは、インデックス列は(c2,c3)であり、クエリでc4列を返す必要があるため、テーブルへのアクセスが必要です。
    is_global_index この演算子がグローバルインデックスをスキャンするかどうかを示します。例えば、Q2のクエリでは、使用されるインデックスが通常のインデックスであるため、is_global_index は false です。Q3のクエリでは、t2 テーブルの i2 インデックスが使用されており、i2 インデックスはグローバルインデックスであるため、is_global_index は true です。
    filter_before_indexback 各 filter に対応し、その filter がインデックス上で直接計算できるか、インデックスからテーブルへのアクセス後に計算する必要があるかを示します。 例えば、Q2のクエリでは、filter が c3 < 1 の場合、インデックス上で直接計算できるため、テーブルへのアクセス回数を削減できます。filter が c4 < 1 の場合、c4 列を取得するためにテーブルへのアクセスが必要であり、その後に計算が可能になります。
    range_key/range/range_cond
    • range_key:インデックスの rowkey 列。
    • range:インデックスのスキャン開始位置と終了位置。全表スキャンであるかどうかを判断するには、range の範囲に注目する必要があります。例えば、rowkey が3列ある場合、range(MIN,MIN, MIN ; MAX, MAX, MAX) は真の意味での全表スキャンを表します。
    • range_cond:インデックスのスキャン開始位置と終了位置を決定する関連述語。
    Q3:
    obclient> CREATE TABLE t2(c1 INT PRIMARY KEY, c2 INT, c3 INT) PARTITION BY HASH(c1) PARTITIONS 4;
    obclient> CREATE INDEX i2 ON t2(c2) GLOBAL;
    obclient> EXPLAIN SELECT * FROM t2 WHERE c2 = 1;
    +-----------------------------------------------------------------+
    | Query Plan                                                      |
    +-----------------------------------------------------------------+
    | ==============================================================  |
    | |ID|OPERATOR                    |NAME  |EST.ROWS|EST.TIME(us)|  |
    | --------------------------------------------------------------  |
    | |0 |DISTRIBUTED TABLE RANGE SCAN|T2(I2)|1       |30          |  |
    | ==============================================================  |
    | Outputs & filters:                                              |
    | -------------------------------------                           |
    |   0 - output([T2.C1], [T2.C2], [T2.C3]), filter(nil), rowset=16 |
    |       access([T2.C1], [T2.C2], [T2.C3]), partitions(p0)         |
    |       is_index_back=true, is_global_index=true,                 |
    |       range_key([T2.C2], [T2.C1]), range(1,MIN ; 1,MAX),        |
    |       range_cond([T2.C2 = 1])                                   |
    +-----------------------------------------------------------------+
    

    上記の例では、実行計画表示の outputs & filters において、TABLE SCAN 演算子の出力情報を以下のように詳細に示しています:

    情報名 意味
    operator TABLE SCAN 演算子の operator には3つの形式があります:TABLE SCAN、TABLE GET、TABLE SKIP SCAN。
    • TABLE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    • TABLE GET は主キーを直接使用して位置特定し、0行または1行のデータを返します。
    • TABLE SKIP SCAN は範囲スキャンに属し、ジャンプ実行で、0行または複数行のデータを返します。
    Q3のクエリでは、DISTRIBUTED TABLE RANGE SCAN はクエリ実行時に分散テーブルに対して区間スキャンを行うことを示します。
    name データにアクセスするために使用するインデックスを選択します。選択したインデックスの名前はテーブル名の後に続きます。インデックス名がない場合、主テーブルスキャンが実行されていることを意味します。ここで注意すべき点は、OceanBaseデータベースでは、主テーブルとインデックスの組織構造が同じであり、主テーブル自体もインデックスであるということです。
    output この演算子の出力列。
    filter この演算子のフィルター述語。例えば、Q1クエリの TABLE GET 演算子では filter が設定されていないため、nil となります。
    partitions スキャンするパーティションを指定します。
    is_index_back この演算子がテーブルへのアクセスを必要とするかどうかを示します。例えば、Q1クエリでは主テーブルが選択されているため、テーブルへのアクセスは不要です。Q2クエリでは、インデックス列が (c2,c3) であり、Q2クエリでは c4 列を返す必要があるため、テーブルへのアクセスが必要です。
    is_global_index この演算子がグローバルインデックスをスキャンするかどうかを示します。例えば、Q2クエリでは通常のインデックスが使用されているため、is_global_index は false です。Q3クエリでは、t2 テーブルの i2 インデックスが使用されており、i2 インデックスはグローバルインデックスであるため、is_global_index は true です。
    filter_before_indexback 各 filter に対応し、その filter がインデックス上で直接計算できるか、インデックスからテーブルへのアクセス後に計算する必要があるかを示します。例えば、Q2クエリでは、filter が c3 < 1 の場合、インデックス上で直接計算できるため、テーブルへのアクセス回数を削減できます。filter が c4 < 1 の場合、c4 列を取得するためにテーブルへのアクセスが必要であり、その後に計算が可能になります。
    range_key/range/range_cond
    • range_key:インデックスの rowkey 列。
    • range:インデックスのスキャン開始位置と終了位置。完全なテーブルスキャンであるかどうかを判断するには、range の範囲に注意する必要があります。例えば、rowkey が3列ある場合、range(MIN,MIN, MIN ; MAX, MAX, MAX) は真の意味での完全なテーブルスキャンを表します。
    • range_cond:インデックスのスキャン開始位置と終了位置を決定する関連述語。

    適用対象

    OceanBaseデータベースのMySQLテナントは、Q4の例にある CONNECT BY LEVEL 構文をサポートしていません。

    Q4:
    obclient> CREATE TABLE t3(pk INT, c1 INT, c2 INT, PRIMARY KEY(pk));
    obclient> INSERT INTO t3 (pk,c1,c2) SELECT LEVEL, MOD(LEVEL,3), LEVEL FROM DUAL CONNECT BY LEVEL <= 10000;
    obclient> CREATE INDEX i1 ON t3(c1,c2);
    obclient> EXPLAIN SELECT /*+ INDEX_SS(t3 i1) */ * FROM t3 WHERE c2 = 1;
    +-----------------------------------------------------------------------------------------+
    | Query Plan                                                                              |
    +-----------------------------------------------------------------------------------------+
    | =================================================                                       |
    | |ID|OPERATOR       |NAME  |EST.ROWS|EST.TIME(us)|                                       |
    | -------------------------------------------------                                       |
    | |0 |TABLE SKIP SCAN|T3(I1)|1       |17          |                                       |
    | =================================================                                       |
    | Outputs & filters:                                                                      |
    | -------------------------------------                                                   |
    |   0 - output([T3.PK], [T3.C1], [T3.C2]), filter([T3.C2 = 1]), rowset=16                 |
    |       access([T3.PK], [T3.C2], [T3.C1]), partitions(p0)                                 |
    |       is_index_back=false, is_global_index=false, filter_before_indexback[false],       |
    |       range_key([T3.C1], [T3.C2], [T3.PK]), range(MIN,MIN,MIN ; MAX,MAX,MAX)always true |
    |       prefix_columns_cnt = 1 , skip_scan_range(1,MIN ; 1,MAX)                           |
    +-----------------------------------------------------------------------------------------+
    

    上記の例では、実行計画表示の outputs & filters において、TABLE SCAN 演算子の出力情報を以下のように詳細に示しています:

    情報名 意味
    operator TABLE SCAN 演算子の operator には3つの形式があります:TABLE SCAN、TABLE GET、TABLE SKIP SCAN。
    • TABLE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    • TABLE GET は主キーを直接使用して位置特定し、0行または1行のデータを返します。
    • TABLE SKIP SCAN は範囲スキャンに属し、ジャンプ実行で、0行または複数行のデータを返します。
    name データにアクセスするために使用するインデックスを選択します。選択したインデックスの名前はテーブル名の後に続きます。インデックス名がない場合は、主テーブルスキャンが実行されていることを意味します。ここで注意すべき点は、OceanBaseデータベースでは、主テーブルとインデックスの組織構造は同じであり、主テーブル自体もインデックスであるということです。
    output この演算子の出力列。
    filter この演算子のフィルター述語。例のQ1クエリでは、TABLE GET 演算子に filter が設定されていないため、nil となります。
    partitions スキャンするパーティションを指定します。
    is_index_back この演算子がテーブルへのアクセスを必要とするかどうかを示します。例えば、Q1クエリでは主テーブルが選択されているため、テーブルへのアクセスは不要です。Q2クエリでは、インデックス列が (c2,c3) であり、Q2クエリでは c4 列を返す必要があるため、テーブルへのアクセスが必要です。
    is_global_index この演算子がグローバルインデックスをスキャンするかどうかを示します。例えば、Q2クエリでは通常のインデックスが使用されているため、is_global_index は false です。Q3クエリでは、t2 テーブルの i2 インデックスが使用されており、i2 インデックスはグローバルインデックスであるため、is_global_index は true です。
    filter_before_indexback 各 filter に対応し、その filter がインデックス上で直接計算できるか、インデックスからテーブルへのアクセス後に計算する必要があるかを示します。例えば、Q2クエリでは、filter が c3 < 1 の場合、インデックス上で直接計算できるため、テーブルへのアクセス回数を削減できます。filter が c4 < 1 の場合、c4 列を取得するためにテーブルへのアクセスが必要であり、その後に計算が可能になります。
    range_key/range/range_cond
    • range_key:インデックスの rowkey 列。
    • range:インデックスのスキャン開始位置と終了位置。完全なテーブルスキャンであるかどうかを判断するには、range の範囲に注意する必要があります。例えば、rowkey が3列ある場合、range(MIN,MIN, MIN ; MAX, MAX, MAX) は真の意味での完全なテーブルスキャンを表します。
    • range_cond:インデックスのスキャン開始位置と終了位置を決定する関連述語。
    prefix_columns_cnt TABLE SKIP SCAN のプレフィックス列の数を表します。
    skip_scan_range TABLE SKIP SCAN のサフィックス列から抽出するスキャン範囲を表します。

    Q4クエリにおいて、TABLE SKIP SCAN は特定の条件を満たす場合に既存のインデックスを利用してスキャンを高速化できます。OceanBaseデータベースは、以下の制限条件を満たす場合に TABLE SKIP SCAN を選択しようとします:

    • テーブルに統計情報が収集されていること。
    • クエリ条件に結合インデックスのサフィックス列が含まれており、他のインデックスの左端のサフィックスではないこと。
    • オプティマイザーがTABLE SKIP SCANと完全なテーブルスキャンのコストを比較した結果、TABLE SKIP SCANの方がコストが低いことを判断した場合。

    適用対象

    OceanBaseデータベースのMySQLテナントでは、現在文字列を数値型に変換する機能はサポートされていません。

    Q5:
    obclient> CREATE TABLE t1(c1 NUMBER PRIMARY KEY, c2 DATE);
    Query OK, 0 rows affected (0.17 sec)
    obclient> CREATE INDEX i1 ON t1(c2);
    Query OK, 0 rows affected (0.51 sec)
    obclient> EXPLAIN SELECT /*+ index(t1 i1) */  c2 FROM t1 WHERE c2 = TIMESTAMP '2024-01-01 11:22:00';
    +-----------------------------------------------------------------------------------------------+
    | Query Plan                                                                                    |
    +-----------------------------------------------------------------------------------------------+
    | ==================================================                                            |
    | |ID|OPERATOR        |NAME  |EST.ROWS|EST.TIME(us)|                                            |
    | --------------------------------------------------                                            |
    | |0 |TABLE RANGE SCAN|T1(I1)|1       |4           |                                            |
    | ==================================================                                            |
    | Outputs & filters:                                                                            |
    | -------------------------------------                                                         |
    |   0 - output([T1.C2]), filter(nil), rowset=16                                                 |
    |       access([T1.C2]), partitions(p0)                                                         |
    |       is_index_back=false, is_global_index=false,                                             |
    |       range_key([T1.C2], [T1.C1]), range(2024-01-01 11:22:00,MIN ; 2024-01-01 11:22:00,MAX),  |
    |       range_cond([cast(T1.C2, TIMESTAMP(19, 9)) = '2024-01-01 11:22:00.000000000'])           |
    +-----------------------------------------------------------------------------------------------+
    

    上記の例では、実行計画表示の outputs & filters において、TABLE RANGE SCAN 演算子の出力情報を以下のように詳細に示しています:

    情報名 意味
    operator TABLE SCAN 演算子の operator には3つの形式があります:TABLE SCAN、TABLE GET、TABLE SKIP SCAN。
    • TABLE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    • TABLE GET は主キーを直接使用して位置特定し、0行または1行のデータを返します。
    • TABLE SKIP SCAN は範囲スキャンに属し、ジャンプ実行で、0行または複数行のデータを返します。
    • TABLE RANGE SCAN は範囲スキャンに属し、0行または複数行のデータを返します。
    name データにアクセスするために使用するインデックスを選択します。選択したインデックスの名前はテーブル名の後に続きます。インデックス名がない場合は、主テーブルスキャンが実行されていることを意味します。ここで注意すべき点として、OceanBaseデータベースでは、主テーブルとインデックスの組織構造は同じであり、主テーブル自体もインデックスです。
    output この演算子の出力列。
    filter この演算子のフィルター述語。例のQ5クエリでは、TABLE RANGE SCAN 演算子に filter が設定されていないため、nil となります。
    partitions スキャンするパーティションを指定します。
    is_index_back この演算子がテーブルへのアクセスを必要とするかどうかを示します。例えば、Q1クエリでは主テーブルが選択されているため、テーブルへのアクセスは不要です。Q2クエリでは、インデックス列が (c2,c3,c1) であり、クエリで c4 列を返す必要があるため、テーブルへのアクセスが必要です。
    is_global_index この演算子がグローバルインデックスをスキャンするかどうかを示します。例えば、Q2クエリでは通常のインデックスが使用されているため、is_global_index は false です。Q3クエリでは、t2 テーブルの i2 インデックスが使用されており、i2 インデックスはグローバルインデックスであるため、is_global_index は true です。
    range_key/range/range_cond
    • range_key:インデックスの rowkey 列。
    • range:インデックスのスキャン開始位置と終了位置。フルテーブルスキャンかどうかを判断するには、range の範囲に注目する必要があります。例えば、rowkey が3列ある場合、range(MIN,MIN, MIN ; MAX, MAX, MAX) は本当の意味でのフルテーブルスキャンを表します。
    • range_cond:インデックスのスキャン開始位置と終了位置を決定する関連述語。

    前のトピック

    実行計画キャッシュ
    最後

    次のトピック

    JOIN
    次