Oracleデータベースエンジニアとしての実力を証明するORACLE MASTER資格。その入り口であるBronze資格の取得は難しくない。本連載と、同時掲載中の連載「Bronze DBA講座」で合格を目指そう!(参考記事:「Oracle 10g対応のORACLE MASTERとは?」)
前回「Oracleで使うSQLの基礎を学ぶ」で、SELECT文の基本的な機能を紹介しました。今回は、SELECT文による行の制限とソートを学びましょう。
1. 確認しておきたい内容
2. WHERE句による行の制限WHERE句による行の制限
問い合わせの行を制限するには、SELECT文でFROM句の直後にWHERE句を使用します。
SELECT {* | [DISTINCT] 列名 | 式} [列別名] [,...] FROM 表名 WHERE 条件式; WHERE 行を制限することの宣言 条件式 {列名 | 定数} 比較条件 {列名 | 定数 | 値リスト}
例:
SQL> SELECT empno, ename FROM emp WHERE empno = 7900;
EMPNO ENAME
---------- ----------
7900 JAMES
比較条件として使用できる演算子には、次のものがあります。
演算子 | 説明 |
---|---|
= | 等しい(左側と右側が等しい) |
> | より大きい(左側が右側より大きい) |
>= | 以上(左側と右側が等しいか、左側が右側より大きい) |
< | より小さい(左側が右側より小さい) |
<= | 以下(左側と右側が等しいか、左側が右側より小さい) |
<>、!=、^= | 等しくない(左側と右側が等しくない) |
BETWEEN .... AND .... | 2つの値の間(2つの値は最小値、最大値の順に記述し、その値も含む) |
IN (値リスト) | 値リストのいずれかと等しい |
LIKE パターン | パターンと等しい |
IS NULL | NULLと等しい |
表1 演算子とその意味 |
<=と>=を記述するときは、=記号は必ず右側にきますので注意しましょう。また、NULLの場合は、「= NULL」としてもエラーにはなりませんが、結果は戻りません。よって「IS NULL」を使用するということに注意しましょう。
次のデータと要件を確認してください。
EMPNO ENAME SAL COMM ----- ------- ------- ------- 7369 SMITH 800 7499 ALLEN 1600 300 7521 WARD 1250 500 7566 JONES 2975
次の文を実行したとき、上記の要件を満たすものはいくつありますか?
SELECT empno, sal*comm FROM emp WHERE comm IS NOT NULL;
a. 1つ
b. 2つ
c. 3つ
d. エラーとなる
正解:a
問題のSELECT文では、「COMMがNULLでない行のSALとCOMMの計算結果を表示する」という結果が戻ります。問題の要件に挙げている要素を満たすには次のことが必要です。
●SALとCOMMを計算した結果を表示する
問題のSELECT文で満たされます。ただし、NULL値を含む式を計算した場合は、計算結果は必ずNULLとなります。
●COMMが0の行を表示しない
「WHERE comm > 0」といった条件が必要です。問題のSELECT文では記述されていないためこの要件は満たされません。
●COMMがNULLの場合は0とする
「NVL(comm, 0)」というようにNVL関数を使用してNULL値を置き換える必要があります。問題のSELECT文ではWHERE句で「comm IS NOT NULL」としたため、COMMがNULLの行が問い合わせ結果に含まれず、この要件は満たされません。
次の文を確認してください。
SELECT empno, ename FROM emp WHERE comm = NULL;
この文の結果に関する説明として正しいものを選択しなさい。
a. COMMがNULLのレコードが戻される
b. エラーとなる
c. レコードは戻されない
d. すべてのレコードが戻される
正解:c
NULL値を検索するには「IS NULL」演算子が必要です。NULL値は値が不明・未割り当てな状態です。空白や「0」とも異なります。上記の文のように「= NULL」とした場合、エラーにはなりませんが、いずれとも等しくないため、レコードは戻されません。
従業員の職種に“SA_”が含まれている行を取り出している問い合わせを選択しなさい。
SELECT empno, ename FROM emp WHERE comm = NULL;
a. SELECT empno, ename FROM emp WHERE job = '%SA_%';
b. SELECT empno, ename FROM emp WHERE job LIKE '%SA\_%' ESCAPE '\';
c. SELECT empno, ename FROM emp WHERE job LIKE "%SA_\%" ESCAPE "\";
d. SELECT empno, ename FROM emp WHERE job LIKE '%SA_\%';
e. SELECT empno, ename FROM emp WHERE job = 'SA_';
正解:b
前回の宿題にした問題です。LIKEキーワードによる文字パターンに一致するかどうかの条件では、「%(0以上の任意の文字の連続)」と「_(任意の1文字)」がワイルドカードになっています。これらのワイルドカードを値として一致させる場合には「ESCAPE」キーワードを使用してエスケープ記号を指定し、ワイルドカードの前に置く必要があります。
WHERE 列名 LIKE '文字パターン' ESCAPE 'エスケープ記号'
今回の問題のように「SA_」で始まるということは、「_」を文字として認識させる必要があります。エスケープ記号を「\」とし、「\_」と指定することで、「_」を文字として認識させています。エスケープ記号は、任意の文字です。文字パターンに含まれないもの(/、$など)を使用するとよいでしょう。
選択肢cのように二重引用符で囲むことはできませんので注意しましょう。
次のCUST表の定義を確認してください。
CUST_ID NOT NULL NUMBER(6) CUST_NAME NOT NULL VARCHAR2(20) CUST_ADDRESS VARCHAR2(20) COUNTRY_ADDRESS VARCHAR2(20) CREDIT_LIMIT NUMBER(9,2)
現在住んでいる国(COUNTRY_ADDRESS)が、フランスである顧客を求めている文を選択しなさい。
a. SELECT cust_id, cust_name FROM cust WHERE LOWER(country_address) = "france"
b. SELECT cust_id, cust_name FROM cust WHERE LOWER(country_address) IS 'france'
c. SELECT cust_id, cust_name FROM cust WHERE LOWER(country_address) LIKE "france"
d. SELECT cust_id, cust_name FROM cust WHERE LOWER(country_address) LIKE 'france'
e. SELECT cust_id, cust_name FROM cust WHERE LOWER(country_address) = '%france%'
正解:d
本来LIKE演算子は文字のパターンマッチのために使用しますが、この問題の「国がフランス」である行を取得できるのは、正解dの文だけです。文字パターンとしての「_」または「%」を使用していないため、このWHERE句は「LOWER(country_address) = 'france'」として動作します。
選択肢eは、一見正しいように見えますが、LIKE演算子ではなく「=」で比較しているため、「%france%」という文字が格納されている行を問い合わせしています。
3. AND、OR、NOTによる論理条件
WHERE句で記述する条件式は、真(TRUE)であると判断された行だけを戻します。WHERE句では、単一の条件式だけでなく、AND、OR、NOTを使用することで条件式を連結することができます。
演算子 | 説明 |
---|---|
AND | 2つの条件式がともにTRUEを戻すときにTRUEとなる |
OR | 2つの条件式のいずれかがTRUEを戻すときにTRUEとなる |
NOT | その条件でない場合にTRUEとなる |
複数の条件があるときは、条件の優先順位に従って処理が行われます。条件式内での優先順位は次のとおりです。
優先順位 | 条件式 |
---|---|
1 | SQL演算子(算術演算子(+、-、*、/)、連結演算子(||)など) |
2 | 比較条件(=、<、<=、>、>=、<>、!=、^=) |
3 | IS NULL、IS NOT NULL、LIKE、IN、NOT IN |
4 | BETWEEN、NOT BETWEEN |
5 | NOT論理条件 |
6 | AND論理条件 |
7 | OR論理条件 |
なお、算術演算子は、「*(乗算)、/(除算)」が先に計算され、「+(加算)、-(減算)」が後に計算されます。これらの優先順位を変更する場合は、「()」を使用します。()で囲まれた条件式は先に処理が行われます。
4. ORDER BY句による行のソート
問い合わせの行をソートして戻すには、SELECT文の最後にORDER BY句を使用します。
SELECT {* | [DISTINCT] 列名 | 式} [列別名] [,...] FROM 表名 [WHERE 条件式] ORDER BY {列名 | 式 | 列別名 | 列位置}[,...] [ASC | DESC]; ORDER BY 行をソートすることの宣言 ASC 行を昇順ソートする(デフォルト) DESC 行を降順ソートする
「列位置」とは、SELECT句の列指定の順に付けた1、2といった番号です。「*」を使用している場合は、表の列定義順に番号が割り当てられます。また、ORDER BY句では、SELECT句の列に付けた列別名も使用できることに注意しましょう。
例:
SQL> SELECT empno, ename, sal FROM emp WHERE deptno=10 ORDER BY 3 DESC;
EMPNO ENAME SAL
---------- ---------- ----------
7839 KING 5000
7782 CLARK 2450
7934 MILLER 1300
複数の列をソート列に指定した場合は、最初に指定したソート列でまずはソートし、最初の列の値が同じものが、2番目に指定したソート列でソートされます。ASCとDESCの指定は、指定した列にのみ影響するので注意しましょう。
データ型の違いによるソートの基準は、次のとおりです。
データタイプ | 昇順ソート | 降順ソート |
---|---|---|
数値データ | 小さい値から順に表示 (例:1、2、3、……) |
大きい値から順に表示 (例:99、98、97、……) |
日付データ | 古い日付から順に表示 (例:2005/01/01、2005/01/02、……) |
新しい日付から順に表示 (例:2005/12/31、2005/12/30、……) |
文字データ | アルファベット順に表示 (例:A、B、……、Z、a、b、……、z) |
アルファベットの逆順に表示 (例:z、y、…a、Z、Y、…A) |
NULL値 | 最後に表示 | 最初に表示 |
次の2つの文を確認してください。
SELECT empno, sal FROM emp ORDER BY sal DESC; SELECT empno, sal FROM emp ORDER BY 2 DESC;
この2つのSELECT文に関する説明として正しいものを選択しなさい。
a. 2つ目の文はempno、salの順にソートが行われる
b. 2つ目の文にsalという別名を指定すると2つの文は同じ結果を表示する
c. 2つ目の文は構文エラーとなる
d. 2つの文は同じ結果を表示する
正解:d
ORDER BY句によるソートは、列名、列別名、列位置のいずれかで指定できます。この問題のsal列の指定は、SELECT句で2番目ですから、「ORDER BY 2」とするのも同じことを指定しています。
選択肢aのempno、salの順にソートを行うには、「ORDER BY 1, 2」と指定する必要があります。
次の文を確認してください。
SELECT ename, hiredate HIRE_DATE FROM emp ORDER BY hiredate DESC;
この文の結果の説明として正しいものを選択しなさい。
a. 日付はデフォルトで大きい順に並ぶため、DESCキーワードは不要
b. 実行時にエラーとなる
c. 正しくhiredate列で降順にソートされて表示される
d. HIRE_DATE別名を指定すれば、正しく降順ソートされて表示される
正解:c
ORDER BY句によるソートは、ASCを付けなくても昇順ソートがデフォルトです。DESCを付けることで降順ソートになります。また、ORDER BY句で指定する列は、列名、列別名、列位置のいずれかを指定できます。
ORDER BY句によるソート処理のデフォルト動作として正しいものを2つ選択しなさい。
a. 昇順にソートされる
b. NULL値は最初に表示される
c. アルファベットはZ-Aの順に表示される
d. 日付は古いものから表示される。
正解:a,d
ORDER BY句によるデフォルトのソート処理には、次の特徴があります。
NULL値は、降順ソート(DESC)を使用した場合は、最初に表示されます。NULL値はほかの値より大きい値として扱われますので注意しましょう。
給与(sal)の高い順にデータを表示している文を選択しなさい。
a. SELECT ename FROM employees ORDER BY sal DESC;
b. SELECT ename FROM employees ORDER BY sal;
c. SELECT ename FROM employees SORT ORDER BY sal DESC;
d. SELECT ename FROM employees SORT ORDER BY sal;
正解:a
ソートしてデータを表示するには、ORDER BY句を使用します。ORDER BYで指定する列には、次のソート順序を指定できます。
問題にある「給与の高い順」にするには、DESCキーワードが必要です。
次の内容をチェックしておきましょう。
次回は、「単一行関数」を確認します。次の宿題を解いておいてください。
次の問い合わせ結果として正しいものを選択しなさい。
SELECT TRUNC(ROUND(MOD(1600, 10), -1), 2) FROM dual;
a. 0
b. 1
c. 0.00
d. エラーとなる
IT資格試験の模擬問題をWebベースで学習できる@IT自分戦略研究所の新サービス「@IT資格攻略」では、Oracle関連の資格をテーマとして取り上げています。Bronze SQL 基礎 I、Bronze DBA 10gも近日中に追加予定です。「無料お試し版」もありますので、記事と併せてご覧ください。
Copyright © ITmedia, Inc. All Rights Reserved.