2016-10-06 4 views
-1

たとえば、2つのテーブルには多数の(または1つの)関係があります。著者と書籍。たとえば、これが新しい著者であり、本が書かれていないかどうかを確認したいとします。SQLite3 - LEFT JOINが他のRDBMSと異なるのはなぜですか?

SELECT authors.id 
FROM authors 
LEFT JOIN books ON authors.id = books.author_id AND books.id IS NULL 

これは、任意のRDBMSで正しく動作します:MySQLの、PostgreSQLのは、SQL Server、Oracleのかもしれないではなく、SQLite3の中で。正しく動作させるには

SELECT authors.id 
FROM authors 
LEFT JOIN books ON authors.id = books.author_id 
WHERE books.id IS NULL 

:SQLite3のでは最後の部分は、WHEREに移動する必要があります。どうして?

+0

玩具データベースはそうです。彼らは非常に大多数のユースケースを扱うので、非常に便利ですが、多くの欠点を抱えて生きることを学ぶ必要があります。 – dasblinkenlight

答えて

2

ON句の条件を持つバージョンでフィルタリングが行われないという誤った点があります。たとえば、hereはMySQL SQL Fiddleであり、条件をON句に入れると2行が返されることを示しています。

これはLEFT JOINを使用して、無冊と著者を取得するための正しい方法である:

SELECT authors.id 
FROM authors LEFT JOIN 
    books 
    ON authors.id = books.author_id 
WHERE books.id IS NULL; 

これが無い本で著者を残して、本を持っている著者を除外します。 LEFT JOINのロジックは簡単です。ONの条件がtrue、false、またはNULLのいずれであるかにかかわらず、すべての行を最初のテーブルに保持します。

ON句に条件を入力するロジックが異なります。それはすべて著者を返すでしょう。フィルタリングはありません。

一部のデータベースの一部のバージョンでは、このような定数式がフィルタリング句として扱われるバグがあります。しかし、それは正しくありません。あなたが「例外」と考えることは正しいですし、どのデータベースでも動作するはずです。

+0

はい、そうです、私は「INNER JOIN」と誤解していると思いますが、「INNER JOIN」の場合、「ON」の条件は「WHERE」と同じです。 –

関連する問題