このエラーの理由は、SQL SELECT
ステートメントは論理的に * 次の順序で処理されます:
-
FROM
:1つまたは複数の結合されたテーブルとON
に一致するすべての行の組み合わせの選択 条件。 -
WHERE
:条件が評価され、一致しない行が削除されます。 -
GROUP BY
:行はグループ化されます(そしてすべてのグループが1つの行に折りたたまれます) -
HAVING
:条件が評価され、一致しない行が削除されます。 -
SELECT
:列のリストが評価されます。 -
DISTINCT
:重複する行が削除されます(SELECT DISTINCTステートメントの場合) -
UNION
、EXCEPT
、INTERSECT
:そのオペランドのアクションは、サブSELECTステートメントの行に対して実行されます。たとえば、UNIONの場合、すべてのサブSELECTステートメントが評価された後、すべての行が収集されます(UNION ALLでない限り、重複は削除されます)。したがって、EXCEPTまたはINTERSECTの場合。 -
ORDER BY
:行は順序付けられています。
したがって、WHERE
では使用できません 句、まだ入力または計算されていないもの。この質問も参照してください:oracle-sql-clause-evaluation-order
データベースエンジンは、クエリに対して別の評価順序を選択することもできます(通常はそれを行います)。唯一の制限は、結果が上記の順序を使用した場合と同じである必要があることです強い> 。
解決策は、クエリを別のクエリで囲むことです。 :
SELECT *
FROM
( SELECT ename
, job
, CASE deptno
WHEN 10 THEN 'ACCOUNTS'
WHEN 20 THEN 'SALES'
ELSE 'UNKNOWN'
END AS department
FROM emp
) tmp
WHERE department = 'SALES' ;
またはWHERE条件で計算を複製する :
SELECT ename
, job
, CASE deptno
WHEN 10 THEN 'ACCOUNTS'
WHEN 20 THEN 'SALES'
ELSE 'UNKNOWN'
END AS department
FROM emp
WHERE
CASE deptno
WHEN 10 THEN 'ACCOUNTS'
WHEN 20 THEN 'SALES'
ELSE 'UNKNOWN'
END = 'SALES' ;
これはクエリの簡略化されたバージョンであるか、次を使用できると思います:
SELECT ename
, job
, 'SALES' AS department
FROM emp
WHERE deptno = 20 ;