Open5
197. Rising Temperature

与えられるテーブル
Weather
テーブル
Column Name | Type | Description |
---|---|---|
id | int | ユニークID |
recordDate | date | 気温を測定した日付。%Y-%m-%d 形式 |
temperature | int | 気温。 |
やること
前日よりも気温が高かった日の id
を求める。
期待される帰結 / 出力
入力
id | recordDate | temperature |
---|---|---|
1 | 2015-01-01 | 10 |
2 | 2015-01-02 | 25 |
3 | 2015-01-03 | 20 |
4 | 2015-01-04 | 30 |
出力
id |
---|
2 |
4 |

方針
LAGを使うか、自己結合するか。LAGのほうが使いやすそうな気がする。

解決方法
WITH compare AS (
SELECT
id,
recordDate AS _date,
LAG(recordDate, 1, NULL) OVER(ORDER BY recordDate) AS prev_date,
temperature AS _temp,
LAG(temperature, 1, NULL) OVER(ORDER BY recordDate) AS prev_temp
FROM
Weather
)
SELECT
id
FROM
compare
WHERE TRUE
AND prev_temp IS NOT NULL
AND DATEDIFF(_date, prev_date) = 1
AND _temp > prev_temp;

メモ
compare
CTE の
recordDate AS _date,
LAG(recordDate, 1, NULL) OVER(ORDER BY recordDate) AS prev_date,
と、
メインのWHERE句の
AND DATEDIFF(_date, prev_date) = 1
は、日付が連続していないことを考慮したほうが実践的かな、という理由。問題では求められていないけど。
MySQL における LAG は、
LAG(expr [, N[, default]]) [null_treatment] over_clause
なので、
LAG(recordDate, 1, NULL) OVER(ORDER BY recordDate) AS prev_date,
は、
LAG(recordDate) OVER(ORDER BY recordDate) AS prev_date,
とできるけれども、明示的に書いたほうが意図が伝わりやすいと思う。
WHERE句で
prev_temp IS NOT NULL
とするのは、最初のレコード(= 前日
がない) を除外したいため。
作成者以外のコメントは許可されていません