tencent cloud

TDSQL-C for MySQL

動向とお知らせ
製品アップデート
製品お知らせ
初心者ガイド
製品概要
プロダクト概要
製品の強み
適用シーン
製品アーキテクチャ
製品仕様
インスタンスタイプ
製品機能一覧
データベースのバージョン
リージョンとアベイラビリティゾーン
基本概念
利用制限
利用ガイドの推奨事項
自社開発カーネル
カーネル概要
カーネルバージョンのアップデート情報
カーネル最適化バージョン
機能特性
パフォーマンス関連機能
セキュリティカテゴリの機能
安定性機能
分析エンジン特性
カーネル問題のチェックと修復
購入ガイド
課金概要
製品価格
クラスタを作成する
構成変更説明
未払いについての説明
継続支払いの説明
返金ポリシー
従量課金から年/月単位サブスクリプションへの変換
従量課金からServerlessへの変換
付加価値サービスの課金説明
料金請求書の確認
クイックスタート
データベース監査
概要
監査インスタンス一覧
監査サービスを有効化する
監査ログの確認
ログ配信
事後アラーム設定
監査ルールの変更
監査サービスを変更する
監査サービスを停止する
監査ルールテンプレート
監査タスクの照会
サブユーザーへのデータベース監査利用権限付与
Serverlessサービス
Serverless入門
サーバーレス版クラスタの作成と管理
伸縮性スケーリング管理ツール
Serverlessリソースパック
マルチAZデプロイ
設定を変更する
よくあるご質問
Serverlessコスト見積ツール
操作ガイド
操作概要
コンソールでのクラスタページビューの切り替え
データベース接続
インスタンス管理
設定を変更する
インスタンス形態管理
クラスタ管理
読み取り専用インスタンス管理 
データベースプロキシ
アカウント管理
DMC
DMC(データベース管理ツール)
パラメータ設定
マルチAZデプロイ
グローバルデータベース
バックアップとリストア
操作ログ
データマイグレーション
パラレルクエリ
列ストレージインデックス CSI
分析エンジン
データベースセキュリティと暗号化
モニタリングとアラーム
SQLの基本操作
以下のコマンドを実行して、TDSQL-C for MySQLに接続してログインします
Tag
実践チュートリアル
TDSQL-C for MySQL データベース監査の等級保護実践
非InnoDBテーブル問題のワンクリック移行検出処理方法
DTSによるデータベースバージョンのアップグレード MySQL 5.7から8.0へ
TDSQL-C for MySQL 使用規範
新版コンソール
データベースプロキシの複数接続アドレスによる複数ROグループの実現
データベースプロキシのメリット
ストレージの課金モードの選び方
DTSによるリモートディザスタリカバリの構築
クラスタ用VPCの作成
データ復旧の方法
CPU使用率の高騰問題の解決方法
サブユーザーへの監視データ閲覧権限付与方法
ホワイトペーパー
セキュリティホワイトペーパー
性能ホワイトペーパー
トラブルシューティング
接続関連
性能関連
よくあるご質問
基本概念
購入と課金
サポートされるフォーマット
接続とネットワーク
機能特性
コンソールの操作
データベーステーブル
パフォーマンスとログ
データベース監査
TDSQL-C for MySQLとTencentDB for MySQLの違い
関連契約
SLA
利用規約
TDSQL-C ポリシー
プライバシーポリシー
データ処理と安全プロトコル
汎用参考
標準と認証
用語一覧
お問い合わせ

ウィンドウ関数の使い方

PDF
フォーカスモード
フォントサイズ
最終更新日: 2025-12-30 16:46:24
ウィンドウ関数はOLAP関数(Online Analytical Processing、オンライン分析処理)とも呼ばれ、データのリアルタイム分析処理を可能にし、分析型データベースにとって非常に重要です。
読み取り専用分析エンジンでは、ウィンドウ関数の使用方法が MySQL 8.0 と基本的に一致します。しかし、同時に、MySQL 5.7 バージョンで有効にされた読み取り専用分析エンジンは、依然としてウィンドウ関数とウィンドウ構文を使用できます。
具体的なウィンドウ使用構文は以下の通りです。
SELECT
<WindowFunction> OVER (PARTITION BY <expr_list> ORDER BY <expr_list> [ASC / DESC] [<WindowFrame>])
FROM
tb_test_window;
SQL文の例:
select studentid,departmentid,classid,math,
row_number() over(partition by departmentid,classid order by math) as row_num
from student_scores;
この例では、グループ化 departmentid、classid 内のデータを math でソートします。

WindowFrame

Frame
ROWSシナリオ
RANGE シナリオ
CURRENT ROW
カレント行。
カレント行と同じすべての行。
UNBOUNDED PRECEDING
先頭行まで。
先頭行まで。
UNBOUNDED
FOLLOWING
最終行まで。
最終行まで。
<N> PRECEDING
前N行。
OrderBy列の値から<N>を引いた値以上である行まで。
<N> FOLLOWING
次のN行。
OrderBy列の値に<N>を足した値以下である行まで。
ROWS | RANGE <Frame>。
ROWS | RANGE BETWEEN <Frame> AND <Frame>。

WindowFunction

現在、ウィンドウ構文でサポートされているウィンドウ関数は以下の表の通りです。
関数名称
機能説明
関数引数
サポートタイプ
ROW_NUMBER()
各パーティション内のデータに行番号を付与します。
-
-
RANK()
各パーティション内のデータに対して非密集型ソートを実行します。
-
-
DENSE_RANK()
各パーティション内のデータに対してデータ集約型ソートを実行します。
-
-
LEAD(<expr>、<offset>、<default>)
現在の行から<offset>行後ろの値を算出し、該当する行がない場合は<default>を返します。
[必須] <expr>:計算列。
すべてのタイプ(三つのパラメータのうちTimeタイプを除く)。
[オプション] <offset>:現在の行から後方へのオフセット行数。デフォルトは1です。
数値型。
[オプション] <default>:計算行が満たされない場合のデフォルト戻り値。デフォルトはNULLを返します。
<expr>タイプと同じです。
LAG(<expr>、<offset>、<default>)
現在の行から<offset>行前方の値を算出し、該当する行がない場合は<default>を返します。
[必須] <expr>:計算列。
すべてのタイプ(三つのパラメータのうちTimeタイプを除く)。
[オプション] <offset>:現在の行から前方へのオフセット行数。デフォルトは1です。
数値型。
[オプション] <default>:計算行が満たされない場合のデフォルト戻り値。デフォルトはNULLを返します。
<expr>タイプと同じです。
FIRST_VALUE(<expr>)
パーティションウィンドウ内の最初の値を計算します。
[必須] <expr>:計算列。
すべてのタイプ。
LAST_VALUE(<expr>)
パーティションウィンドウ内の最後の値を計算します。
[必須] <expr>:計算列。
すべてのタイプ。
MIN(<expr>)
パーティションウィンドウ内でOrderBy列の最小値の行における<expr>値を計算します。
[必須] <expr>:計算列。
すべてのタイプ。
MAX(<expr>)
パーティションウィンドウ内でOrderBy列の最大値の行における<expr>値を計算します。
[必須] <expr>:計算列。
すべてのタイプ。
COUNT(<expr>)
パーティションウィンドウ内のデータの総行数を計算します。
[必須] <expr>:計算列。
すべてのタイプ。
SUM(<expr>)
パーティションウィンドウ内のデータの合計を計算します。
[必須] <expr>:計算列。
数値型。
AVG(<expr>)
パーティションウィンドウ内のデータの平均値を計算します。
[必須] <expr>:計算列。
数値型。
数値型:int、bigint、float、double、decimal。
文字列型:char、varchar。
時間型:date、time、datetime、timestamp。

詳細ケース

事例テーブル作成文:
drop table if exists test.tb_window;
create table test.tb_window (c1 int not null primary key, c2 int, c3 int);
create table test.tb_window (c1 Int32, c2 Nullable(Int32), c3 Nullable(Int32)) engine = LibraTree order by (c1);
insert into test.tb_window values (1, 1, 1), (2, 1, 1), (3, 1, 2), (4, 1, 4), (5, 1, 6), (6, 1, 6);

ROWS キーワード

説明:
このキーワードは行単位でウィンドウサイズを統計し、ウィンドウ内のデータに対して計算を行います。
-- 事例文
mysql> select c2, c3, COUNT(c1) over (partition by c2 order by c3 ROWS BETWEEN CURRENT ROW AND 2 FOLLOWING) cn from test.tb_window;
+----+----+----+
| c2 | c3 | cn |
+----+----+----+
| 1 | 1 | 3 | -- ウィンドウ行インデックス範囲: current -> 後2行 [0 ~ 2]
| 1 | 1 | 3 | -- ウィンドウ行インデックス範囲: current -> 後2行 [1 ~ 3]
| 1 | 2 | 3 | -- ウィンドウ行インデックス範囲: current -> 後2行 [2 ~ 4]
| 1 | 4 | 3 | -- ウィンドウ行インデックス範囲: current -> 後2行 [3 ~ 5]
| 1 | 6 | 2 | -- ウィンドウ行インデックス範囲: current -> 後1行 [4 ~ 5] (後方に1行のみ存在)
| 1 | 6 | 1 | -- ウィンドウ行インデックス範囲: current (後方にデータがありません)
+----+----+----+
6 rows in set (0.06 sec)

RANGE キーワード

説明:
このキーワードは値に基づいてウィンドウサイズを統計し、ウィンドウ内のデータに対して計算を行います。例えば、以下のSQLケースでは、C3列の現在行の値に2を加えた後、対応する行の位置を見つけ、現在行までの間が一つのウィンドウとなります。
-- 事例文
mysql> select c2, c3, COUNT(c1) over (partition by c2 order by c3 RANGE BETWEEN CURRENT ROW AND 2 FOLLOWING) cn from test.tb_window;
+----+----+----+
| c2 | c3 | cn |
+----+----+----+
| 1 | 1 | 3 | -- ウィンドウ行インデックス範囲: カレント -> 3に対応する行インデックス間の行データ [0 ~ 2]
| 1 | 1 | 3 |
| 1 | 2 | 2 | -- ウィンドウ行インデックス範囲: カレント -> 4に対応する行インデックス間の行データ [2 ~ 3]
| 1 | 4 | 3 | -- ウィンドウ行インデックス範囲: カレント -> 6に対応する行インデックス間の行データ [3 ~ 5]
| 1 | 6 | 2 | -- ウィンドウ行インデックス範囲: カレント -> 8に対応する行インデックス間の行データ [4 ~ 5]
| 1 | 6 | 2 |
+----+----+----+
6 rows in set (0.06 sec)

ROW_NUMBER

説明:
この関数はパーティション内のデータに対して番号付けを行い、<WindowFrame>の制限を受けません。
-- 事例文
mysql> select c2, c3, ROW_NUMBER() over (partition by c2 order by c3) rn from test.tb_window;
+----+----+------+
| c2 | c3 | rn |
+----+----+------+
| 1 | 1 | 1 |
| 1 | 1 | 2 |
| 1 | 2 | 3 |
| 1 | 4 | 4 |
| 1 | 6 | 5 |
| 1 | 6 | 6 |
+----+----+------+
6 rows in set (0.04 sec)

RANK & DENSE_RANK

RANK 関数:パーティション内部のデータに対して非密集型ランキングを行い、この関数は <WindowFrame> の制限を受けません。
DESC_RANK関数:パーティション内部のデータに対して密集型ランキングを行い、この関数は <WindowFrame> の制限を受けません。
-- 事例文
select
c2, c3,
RANK() over (partition by c2 order by c3) rk,
DENSE_RANK() over (partition by c2 order by c3) drk
from test.tb_window;
+------+------+------+------+
| c2 | c3 | rk | drk |
+------+------+------+------+
| 1 | 1 | 1 | 1 |
| 1 | 1 | 1 | 1 |
| 1 | 2 | 3 | 2 |
| 1 | 4 | 4 | 3 |
| 1 | 6 | 5 | 4 |
| 1 | 6 | 5 | 4 |
+------+------+------+------+
6 rows in set (0.05 sec)

LEAD & LAG

一、1パラメータシナリオ

LEAD(<expr>)関数:パーティション内のカレント行の次の行のデータを計算します。次の行がない場合はデフォルトでNULLを補充します。この関数は <WindowFrame> の制限を受けません。
LAG(<expr>)関数:パーティション内のカレント行の前の行のデータを計算します。前の行がない場合はデフォルトでNULLを補充します。この関数は <WindowFrame> の制限を受けません。
-- 事例文
mysql> select
c2, c3,
LEAD(c3) over (partition by c2 order by c3) ld,
LAG(c3) over (partition by c2 order by c3) lg
from test.tb_window;
+------+------+------+------+
| c2 | c3 | ld | lg |
+------+------+------+------+
| 1 | 1 | 1 | NULL |
| 1 | 1 | 2 | 1 |
| 1 | 2 | 4 | 1 |
| 1 | 4 | 6 | 2 |
| 1 | 6 | 6 | 4 |
| 1 | 6 | NULL | 6 |
+------+------+------+------+
6 rows in set (0.11 sec)

二、2つのパラメータシナリオ

LEAD(<expr>, <offset>)関数:パーティション内のカレント行の後方<offset>行のデータを計算します。後方<offset>行がない場合はデフォルトでNULLを補充します。この関数は<WindowFrame>の制限を受けません。
LAG(<expr>, <offset>)関数:パーティション内のカレント行の前方<offset>行のデータを計算します。前方<offset>行がない場合はデフォルトでNULLを補充します。この関数は<WindowFrame>の制限を受けません。
-- 事例文
mysql> select
c2, c3,
LEAD(c3, 2) over (partition by c2 order by c3) ld,
LAG(c3, 2) over (partition by c2 order by c3) lg
from test.tb_window;
+------+------+------+------+
| c2 | c3 | ld | lg |
+------+------+------+------+
| 1 | 1 | 2 | NULL |
| 1 | 1 | 4 | NULL |
| 1 | 2 | 6 | 1 |
| 1 | 4 | 6 | 1 |
| 1 | 6 | NULL | 2 |
| 1 | 6 | NULL | 4 |
+------+------+------+------+
6 rows in set (0.07 sec)

3、3つのパラメータシナリオ

LEAD(<expr>, <offset>, <default>)関数:パーティション内のカレント行の後方<offset>行のデータを計算します。後方<offset>行がない場合は<default>を補充します。この関数は<WindowFrame>の制限を受けません。
LAG(<expr>, <offset>, <default>>)関数:パーティション内のカレント行の前方<offset>行のデータを計算します。前方<offset>行がない場合は<default>を補充します。この関数は<WindowFrame>の制限を受けません。
-- 事例文
mysql> select
c2, c3,
LEAD(c3, 2, 1000) over (partition by c2 order by c3) ld,
LAG(c3, 2, 1000) over (partition by c2 order by c3) lg
from test.tb_window;
+------+------+------+------+
| c2 | c3 | ld | lg |
+------+------+------+------+
| 1 | 1 | 2 | 1000 |
| 1 | 1 | 4 | 1000 |
| 1 | 2 | 6 | 1 |
| 1 | 4 | 6 | 1 |
| 1 | 6 | 1000 | 2 |
| 1 | 6 | 1000 | 4 |
+------+------+------+------+
6 rows in set (0.10 sec)

FIRST_VALUE & LAST_VALUE

FIRST_VALUE(<expr>)関数:パーティション内ウィンドウの最初の値を計算します(OrderBy c3を指定した場合、c3列の最初の値に重複データが存在すると、first_value(c4)の結果は不安定になる可能性があります)。
LAST_VALUE(<expr>)関数:パーティション内ウィンドウの最後の値を計算します(OrderBy c3を指定した場合、c3列の最後の値に重複データが存在すると、last_value(c4)の結果は不安定になる可能性があります)。
-- 事例文
mysql> select
c2, c3,
FIRST_VALUE(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) fv,
LAST_VALUE(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) lv
from test.tb_window;
+------+------+------+------+
| c2 | c3 | fv | lv |
+------+------+------+------+
| 1 | 1 | 1 | 6 |
| 1 | 1 | 1 | 6 |
| 1 | 2 | 1 | 6 |
| 1 | 4 | 1 | 6 |
| 1 | 6 | 1 | 6 |
| 1 | 6 | 1 | 6 |
+------+------+------+------+
6 rows in set (0.07 sec)

MIN & MAX

MIN(<expr>)関数:パーティション内ウィンドウの最小値を計算します。
MAX(<expr>)関数:パーティション内ウィンドウの最大値を計算します。
-- 事例文
mysql> select
c2, c3,
MIN(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) mi,
MAX(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) ma
from test.tb_window;
+------+------+------+------+
| c2 | c3 | mi | ma |
+------+------+------+------+
| 1 | 1 | 1 | 6 |
| 1 | 1 | 1 | 6 |
| 1 | 2 | 1 | 6 |
| 1 | 4 | 1 | 6 |
| 1 | 6 | 1 | 6 |
| 1 | 6 | 1 | 6 |
+------+------+------+------+
6 rows in set (0.07 sec)

COUNT

説明:
パーティション内ウィンドウのデータ総行数を算出します。
-- 事例文
mysql> select c2, c3, COUNT(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) c from test.tb_window;
+------+------+----+
| c2 | c3 | c |
+------+------+----+
| 1 | 1 | 6 |
| 1 | 1 | 6 |
| 1 | 2 | 6 |
| 1 | 4 | 6 |
| 1 | 6 | 6 |
| 1 | 6 | 6 |
+------+------+----+
6 rows in set (0.04 sec)

SUM

説明:
パーティション内ウィンドウのデータ合計を算出します。
-- 事例文
mysql> select c2, c3, SUM(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) s from test.tb_window;
+------+------+------+
| c2 | c3 | s |
+------+------+------+
| 1 | 1 | 20 |
| 1 | 1 | 20 |
| 1 | 2 | 20 |
| 1 | 4 | 20 |
| 1 | 6 | 20 |
| 1 | 6 | 20 |
+------+------+------+
6 rows in set (0.06 sec)

AVG

説明:
パーティション内ウィンドウのデータ平均値を算出します。
-- 事例文
mysql> select c2, c3, AVG(c3) over (partition by c2 order by c3 ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) a from test.tb_window;
+------+------+--------+
| c2 | c3 | a |
+------+------+--------+
| 1 | 1 | 3.3333 |
| 1 | 1 | 3.3333 |
| 1 | 2 | 3.3333 |
| 1 | 4 | 3.3333 |
| 1 | 6 | 3.3333 |
| 1 | 6 | 3.3333 |
+------+------+--------+
6 rows in set (0.06 sec)


ヘルプとサポート

この記事はお役に立ちましたか?

フィードバック