選択する
SELECTステートメントは、TiDB からデータを読み取るために使用されます。
あらすじ
SelectStmt:

デュアルから:

Where句オプション:

SelectStmtOpts:

SelectStmtFieldList:

TableRefsClause:
- TableRefsClause
 - AsOfClause
 
TableRefsClause ::=
    TableRef AsOfClause? ( ',' TableRef AsOfClause? )*
AsOfClause ::=
    'AS' 'OF' 'TIMESTAMP' Expression
Where句オプション:

SelectStmtGroup:

有節:

OrderByオプション:

SelectStmtLimit:

最初または次:

FetchFirstOpt:

行または行:

SelectLockOpt:
- SelectLockOpt
 - TableList
 
SelectLockOpt ::=
    ( ( 'FOR' 'UPDATE' ( 'OF' TableList )? 'NOWAIT'? )
|   ( 'LOCK' 'IN' 'SHARE' 'MODE' ) )?
TableList ::=
    TableName ( ',' TableName )*
WindowClauseOptional

構文要素の説明
| 構文要素 | 説明 | 
|---|---|
TableOptimizerHints | これは、TiDB のオプティマイザーの動作を制御するためのヒントです。詳細については、 オプティマイザーのヒントを参照してください。 | 
ALL 、 DISTINCT 、 DISTINCTROW | ALL 、 DISTINCT / DISTINCTROW修飾子は、重複する行を返すかどうかを指定します。 ALL (デフォルト) は、一致するすべての行を返すことを指定します。 | 
HIGH_PRIORITY | HIGH_PRIORITYを指定すると、現在のステートメントが他のステートメントよりも優先されます。 | 
SQL_CALC_FOUND_ROWS | TiDB はこの機能をサポートしていないため、 tidb_enable_noop_functions=1が設定されていないとエラーが返されます。 | 
SQL_CACHE 、 SQL_NO_CACHE | SQL_CACHEとSQL_NO_CACHEは、リクエスト結果を TiKV (RocksDB) のBlockCacheにキャッシュするかどうかを制御するために使用されます。 count(*)クエリなど、大量のデータに対する 1 回限りのクエリの場合は、ホット ユーザー データがBlockCacheにフラッシュされないようにSQL_NO_CACHEに入力することをお勧めします。 | 
STRAIGHT_JOIN | STRAIGHT_JOINを指定すると、オプティマイザはFROM句で使用されるテーブルの順序でユニオン クエリを実行するようになります。オプティマイザーが不適切な結合順序を選択した場合、この構文を使用してクエリの実行を高速化できます。 | 
select_expr | それぞれのselect_exprは、取得する列を示します。列名と式を含みます。 \*はすべての列を表します。 | 
FROM table_references | FROM table_references句は、行を取得するテーブル ( select * from t;など)、テーブル ( select * from t1 join t2;など)、または 0 テーブル ( select 1+1;に相当するselect 1+1 from dual;など) を示します。 | 
WHERE where_condition | WHERE節が指定されている場合、行が選択されるために満たさなければならない条件を示します。結果には、条件を満たすデータのみが含まれます。 | 
GROUP BY | GROUP BYステートメントは、結果セットをグループ化するために使用されます。 | 
HAVING where_condition | HAVING節とWHERE節は両方とも、結果をフィルター処理するために使用されます。 HAVING句はGROUP BYの結果をフィルター処理し、 WHERE句は集計前の結果をフィルター処理します。 | 
ORDER BY | ORDER BY句は、 select_exprリストの列、式、または項目に基づいて、昇順または降順でデータを並べ替えるために使用されます。 | 
LIMIT | LIMIT句を使用して、行数を制限できます。 LIMITは、1 つまたは 2 つの数値引数を取ります。引数を 1 つ指定すると、返される行の最大数が指定されます。返される最初の行は、デフォルトではテーブルの最初の行です。 2 つの引数がある場合、最初の引数は返す最初の行のオフセットを指定し、2 番目の引数は返す行の最大数を指定します。 TiDB はFETCH FIRST/NEXT n ROW/ROWS ONLY構文もサポートしており、これはLIMIT nと同じ効果があります。この構文ではnを省略でき、その効果はLIMIT 1と同じです。 | 
Window window_definition | これはウィンドウ関数の構文で、通常は分析計算を行うために使用されます。詳細については、 ウィンドウ関数を参照してください。 | 
FOR UPDATE | SELECT FOR UPDATE句は、結果セット内のすべてのデータをロックして、他のトランザクションからの同時更新を検出します。現在のトランザクションの開始後に他のトランザクションによって書き込まれた行データなど、クエリ条件に一致するが結果セットに存在しないデータは読み取りロックされません。 TiDB は楽観的な取引モデルを使用します。ステートメント実行フェーズでは、トランザクションの競合は検出されません。したがって、現在のトランザクションは、PostgreSQL などの他のデータベースのように、他のトランザクションがUPDATE 、 DELETEまたはSELECT FOR UPDATEを実行することをブロックしません。コミット フェーズでは、 SELECT FOR UPDATEによって読み取られた行は 2 つのフェーズでコミットされます。つまり、競合検出にも参加できます。書き込みの競合が発生すると、 SELECT FOR UPDATE句を含むすべてのトランザクションでコミットが失敗します。競合が検出されない場合、コミットは成功します。また、ロックされた行に対して新しいバージョンが生成されるため、コミットされていない他のトランザクションが後でコミットされるときに、書き込みの競合を検出できます。ペシミスティック トランザクション モードを使用する場合、動作は基本的に他のデータベースと同じです。詳細はMySQL InnoDB との違いをご覧ください。 TiDB はFOR UPDATEのNOWAIT修飾子をサポートしています。詳しくはTiDB ペシミスティック トランザクション モードをご覧ください。 | 
LOCK IN SHARE MODE | 互換性を保証するために、TiDB はこれら 3 つの修飾子を解析しますが、無視します。 | 
例
mysql> CREATE TABLE t1 (id INT NOT NULL PRIMARY KEY AUTO_INCREMENT, c1 INT NOT NULL);
Query OK, 0 rows affected (0.11 sec)
mysql> INSERT INTO t1 (c1) VALUES (1),(2),(3),(4),(5);
Query OK, 5 rows affected (0.03 sec)
Records: 5  Duplicates: 0  Warnings: 0
mysql> SELECT * FROM t1;
+----+----+
| id | c1 |
+----+----+
|  1 |  1 |
|  2 |  2 |
|  3 |  3 |
|  4 |  4 |
|  5 |  5 |
+----+----+
5 rows in set (0.00 sec)
MySQL の互換性
- 構文
SELECT ... INTO @variableはサポートされていません。 - 構文
SELECT ... GROUP BY ... WITH ROLLUPはサポートされていません。 - 構文
SELECT .. GROUP BY exprは、 MySQL 5.7のようにGROUP BY expr ORDER BY exprを意味しません。代わりに、TiDB は MySQL 8.0 の動作と一致し、デフォルトの順序を意味しません。