質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
SQL

SQL(Structured Query Language)は、リレーショナルデータベース管理システム (RDBMS)のデータベース言語です。大きく分けて、データ定義言語(DDL)、データ操作言語(DML)、データ制御言語(DCL)の3つで構成されており、プログラム上でSQL文を生成して、RDBMSに命令を出し、RDBに必要なデータを格納できます。また、格納したデータを引き出すことも可能です。

Q&A

2回答

1735閲覧

sql ウィンドウ関数

m.g2017

総合スコア19

SQL

SQL(Structured Query Language)は、リレーショナルデータベース管理システム (RDBMS)のデータベース言語です。大きく分けて、データ定義言語(DDL)、データ操作言語(DML)、データ制御言語(DCL)の3つで構成されており、プログラム上でSQL文を生成して、RDBMSに命令を出し、RDBに必要なデータを格納できます。また、格納したデータを引き出すことも可能です。

0グッド

0クリップ

投稿2018/02/26 12:03

SQL実践入門(ミック 著)のリスト5.8「ウィンドウ関数による解」の以下のsqlが理解できません。
(MIN ~ AS min_codeの部分の処理)
OVER句での処理詳細とMIN()のなかの処理詳細について解説お願いします。

テーブル名:PostalCode(郵便番号)
カラム名:pcode(郵便番号), district_name(地域名)
4130001      静岡県熱海市泉
4130002      静岡県熱海市伊豆山
4130103      静岡県熱海市綱代
4130041      静岡県熱海市青葉町
4103213      静岡県伊豆市青羽根
4380824      静岡県磐田市赤池

SELECT pcode,
district_name
FROM (SELECT pcode,
district_name,
CASE WHEN pcode = '4130033' THEN 0
WHEN pcode LIKE '413003%' THEN 1
WHEN pcode LIKE '41300%' THEN 2
WHEN pcode LIKE '4130%' THEN 3
WHEN pcode LIKE '413%' THEN 4
WHEN pcode LIKE '41%' THEN 5
WHEN pcode LIKE '4%' THEN 6
ELSE NULL END AS hit_code,
MIN(CASE WHEN pcode = '4130033' THEN 0
WHEN pcode LIKE '413003%' THEN 1
WHEN pcode LIKE '41300%' THEN 2
WHEN pcode LIKE '4130%' THEN 3
WHEN pcode LIKE '413%' THEN 4
WHEN pcode LIKE '41%' THEN 5
WHEN pcode LIKE '4%' THEN 6
ELSE NULL END)
OVER(ORDER BY CASE WHEN pcode = '4130033' THEN 0
WHEN pcode LIKE '413003%' THEN 1
WHEN pcode LIKE '41300%' THEN 2
WHEN pcode LIKE '4130%' THEN 3
WHEN pcode LIKE '413%' THEN 4
WHEN pcode LIKE '41%' THEN 5
WHEN pcode LIKE '4%' THEN 6
ELSE NULL END) AS min_code
FROM PostalCode) Foo
WHERE hit_code = min_code;

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2018/02/27 00:55

おそらくPostgreSQLの案件かと思われますので、そうであれば質問にPostgreSQLタグをつけたらよいかと思います。また、手元の環境で試したい場合は、 http://gihyo.jp/book/2015/978-4-7741-7301-6/support のサポートページからサンプルコードをダウンロードし、Code5.txtを参照すると該当するものが見つかります。「■リスト5.5 郵便番号テーブルの定義」のあたり。
guest

回答2

0

CASEでの記述部分が冗長なので、見渡し易くする為に纏めます。

SQL

1SELECT pcode, district_name 2FROM ( 3 SELECT * 4 , MIN(hit_code) OVER(ORDER BY hit_code) AS min_code 5 FROM ( 6 SELECT 7 pcode, district_name 8 , CASE 9 WHEN pcode = '4130033' THEN 0 10 WHEN pcode LIKE '413003%' THEN 1 11 WHEN pcode LIKE '41300%' THEN 2 12 WHEN pcode LIKE '4130%' THEN 3 13 WHEN pcode LIKE '413%' THEN 4 14 WHEN pcode LIKE '41%' THEN 5 15 WHEN pcode LIKE '4%' THEN 6 16 ELSE NULL 17 END AS hit_code 18 FROM PostalCode 19 ) Foo 20) Foo2 21WHERE hit_code = min_code;

全体からすると、hit_codeの最小の行を取り出すのが目的のSQLとなっています。
目的に対して、OVER()記述には意味がありません。
また、where条件が無かったとしても、hit_code順のhit_codeの最小値ということでは、これも意味がありません。

全体で見にくいですし、Min() over()の説明の例題だとしたら、あまり適当とは言えませんね。

投稿2018/02/27 00:50

編集2018/02/27 08:50
sazi

総合スコア25138

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

回答からはずれます。

質問のプログラムコードは対応しているMarkdownの機能 の[コードを入力]で修正してください。

同じSQLでも方言が大きいですから、どのデータベースを使うのかをタグで明示した方が適切なコメントが付き易いです。
SQLを実行するにはCREATE TABLE文とテーブルにデータを入れるにはINSERT文があると質問のSELECT文を実行して動作確認してくれる奇特な人が増えそうです。

パッと見、

SQL

1WHEN pcode LIKE '41300%' THEN 2

に3件しかないし、 hit_code と min_code は同じでしょう。
それが意味があるようには思えませんし、意味にもなくわざわざこんなに複雑なSQLを書くのは実用的ではありません。

投稿2018/02/26 21:59

Orlofsky

総合スコア16415

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2018/02/27 01:01 編集

データ構造や格納データを見ればわかることを、 SQLで説明して「こういう結果を得るためにこういう方法が使える」という一環で ウィンドウ関数を駆使した場合の一例なんだと思います。 一発のSELECT文で2つの結果を得るために無駄に連結しているのでしょう。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問