SQL問題を自分の中に定着させるために、パターンごとの問い合わせをまとめます。
※随時更新
###予約語の例
DISTINCT:重複を排除して表示する
CURRENT_DATE:現在の日付を返す
CURRENT_TIME:現在の時刻を返す
CURRENT_TIMESTAMP:現在の日付と時刻を返す
#####TABLE:社員マスター(社員番号、社員名、性別、生年月日)
###データ操作言語の基本4つ
SELECT * FROM 社員マスター
INSERT INTO 社員マスター VALUES('001','佐藤 正','男','19900410')
UPDATE 社員マスター SET 生年月日='19900411' WHERE 社員番号='001'
DELETE FROM 社員マスター WHERE 社員番号='001'
###SELECT文の文法
--1990年生まれの社員を遅く生まれた順に並べて6番目~15番目を表示する
SELECT * FROM 社員マスター
WHERE 生年月日 LIKE '1990%'
ORDER BY 生年月日 DESC LIMIT 10 OFFSET 5
--1990年生まれの社員を性別ごとに分けて20人以上いる場合のみ人数を表示する
SELECT 性別,COUNT(*) FROM 社員マスター
WHERE 生年月日 LIKE '1990%'
GROUP BY 性別
HAVING COUNT(*) >= 20
###データ定義言語の例
--社員番号を主キーとして社員マスターを作成する
CREATE TABLE 社員マスター(
社員番号 integer,社員名 text,性別 text,生年月日 date,
PRIMARY KEY(社員番号))
--[ユーザー名]の人に社員マスターのSELECT文を実行する権限を与える
GRANT SELECT ON 社員マスター TO [ユーザー名]
##副問合せの例
主問合せから1行ずつ副問合せにいき処理をする。
###男女それぞれの最年長の人を除く全ての社員を取り出す
#####TABLE:社員(社員番号、社員名、性別、生年月日)
select 社員番号,社員名 from 社員 as S1
where 生年月日 > (select MIN(生年月日) from 社員 as S2
where S1.性別 = S2.性別);
ポイント
・MIN(生年月日)で最年長の人の生年月日を取得している
生年月日なのでMAXではなくMINであることに注意
・副問合せのwhere句で性別の条件を入れている
最年長ではない男性(Aさんとします)の行においては、まず副問合せで性別が男性という条件のもので最年長の生年月日を出し、それを主問合せに渡します。この際に主問合せの条件(2行目のwhere 生年月日)で、男性の最年長の生年月日と比べて大きいので条件を満たし、Aさんの社員番号と社員名が取得されます。
逆に最年長の男性(Bさんとします)は、副問合せで自分の生年月日が取得され、それと主問合せで(where 自分の生年月日 > 自分の生年月日)となるので条件を満たさず、Bさんのデータは取得されません。女性として考えても同様なので、これによって男女それぞれの最年長の社員が除かれてデータが取得されます。
###FE資格を取っている社員の中でAPも取得しているか否かを抽出する
#####TABLE:社員取得資格(社員コード、資格)
社員コード | 資格 |
---|---|
S001 | FE |
S001 | AP |
S001 | DB |
S002 | FE |
S002 | SM |
S003 | FE |
S004 | AP |
S005 | NULL |
select 社員コード,A.資格 as 資格1,B.資格 as 資格2
from 社員取得資格 as A
LEFT OTHER JOIN 社員取得資格 as B
on A.社員コード = B.社員コード and A.資格 = 'FE' and B.資格 = 'AP'
where A.資格 = 'FE'
;
ポイント
・キーは(社員コード、資格)の複合キー
・1つの資格列の中にFEとAPの取得情報があるため、それらを分離して表示するために自己結合する必要があります。さらに、AP取得情報のみを表示したいので結合するテーブルに資格がAPである条件も必要です。
社員コード | 資格1 | 資格2 |
---|---|---|
S001 | FE | AP |
S001 | AP | NULL |
S001 | DB | NULL |
S002 | FE | NULL |
S002 | SM | NULL |
S003 | FE | NULL |
S004 | AP | NULL |
S005 | NULL | NULL |
・左外部結合により、上記表のように結合される列はそのまま残るため、FEを取得しているという条件で抽出しなければならないので、where句で指定すると結果がでます。
社員コード | 資格1 | 資格2 |
---|---|---|
S001 | FE | AP |
S002 | FE | NULL |
S003 | FE | NULL |