2012-03-28 2 views
5

私は、ANSI-92 SQL標準を学ぶためにしようとしているが、私はそれを完全に理解していないようだ(私は一般的にだけでなく、ANSI-89標準にし、データベースに新たなんです)。結合を誤解していますか?

私の例では、私は3つのテーブルkingdom - <ファミリー - <種(生物学分類)を持っています。

  • 種や家系のない王国があるかもしれません。
  • 種もkindgomsのない家族があるかもしれません。
  • 王国や家族のない種があるかもしれません。

なぜこれが起こるかもしれませんか?

はここなど、生物学者は、新しい種を見つけたが、彼は王国や家族にこれを分類していない、何の種を持っていないし、それが属している必要があり何王国わからない新しいファミリを作成

を言いますhttp://sqlfiddle.com/#!4/015d1/3

私はすべての王国、すべての種が私を検索するクエリを作成しますが、種を持たない家族は検索しませんので、私はこれを行います。私はこれはと思う何

select * 
    from reino r 
     left join (
      familia f    
      right join especie e 
       on f.fnombre = e.efamilia 
       and f.freino = e.ereino 
     ) on r.rnombre = f.freino 
      and r.rnombre = e.ereino; 

は次のとおりです。

  1. が参加する権利として、家族や種に参加し、それはすべての種をもたらしますが、そうではない何の種を持っていないものを家族。したがって、ある種が家族に分類されていない場合、それは家族にはnullで表示されます。

  2. その後、左が参加するように、結果に王国に参加するので、それは何の家族やその王国に分類された種が存在しない場合でも、すべての王国をもたらします。

私は間違っていますか?分類されていない種を私に見せてはいけませんか?内側のクエリを実行すると、必要なものが表示されます。私は物事をグループ化している問題がありますか?

+0

これは、Oracleが行うクエリの最適化を台無しに?私のクエリでは、括弧は不要ですしていますか?私は同じ結果を得ますか?オラクルの指示は何ですか? – Roger

+0

@outis私は結合構文が入れ子になっていないと敬意を表する必要があります。 [この記事ではこのトピックについて論じていると思います](http://tonyhasler.wordpress.com/2009/02/22/parentheses-in-ansi-join-syntax/)、括弧を使って複数の表を結合するときの操作 –

+0

@MichaelFredrickson:私は正しかった。そこにはSQL/Foundation§7.6があります。 – outis

答えて

2

あなたは#1のあなたの説明で正しい...あなたのクエリの問題は、ステップ#2です。

あなたは(家族&種)、あなたは一致がない場合でも、すべての王国を要求している(家族&種)に王国からleft joinを行うと...しかし、これはあなたに(家族を返しません&種族)の組み合わせがあります。

近いクエリは次のようになります。left joinfull joinに変更した

select * 
    from reino r 
     full join (
      familia f    
      right join especie e 
       on f.fnombre = e.efamilia 
       and f.freino = e.ereino 
     ) on r.rnombre = f.freino 
      and r.rnombre = e.ereino; 

お知らせ...

ただし、これは種に関連付けられているファミリを返すだけです。王国に関連付けられているが種は含まれていないファミリは返されません。さらに考えでは、あなたはそうのようなクエリを再記述することができます:

select * 
from 
    especie e 
    left join familia f 
     on f.fnombre = e.efamilia 
     and f.freino = e.ereino 
    full join reino r 
     on r.rnombre = f.freino 
     and r.rnombre = e.ereino; 

あなたの質問を再読み込みした後、これは


EDITは...実際にあなたが望んでいたしたいです

私はこれが好きかもしれないと思うのは、普通は貧弱なスタイルであることに悩まされているRIGHT JOINを排除しているからです。そして結果がどうなるかを判断するために人々が正しく解析することが難しい括弧。

+0

ありがとうございます、今は物事がより明確です。時間をとっていただきありがとうございます:) – Roger

+0

ただもう一つ質問。 outisから作られた私の質問にコメントを読んでください。かっこは不要ですか?これはオラクルオプティマイザで混乱しますか? – Roger

+0

私は@outisに同意しません...しかし、私は主にSQL Serverで作業するので、これはOracleでは異なる場合があります。しかし、私の経験では、かっこは結果と実行計画の両方に影響します。 [これはOracleでこれを確認すると思う情報源です。](http://tonyhasler.wordpress.com/2009/02/22/parentheses-in-ansi-join-syntax/)...私はかっこを使用せずにそのクエリをどのように再構成するのかは分かりませんが(おそらくそれをサブ選択に変更する必要があります)、可能であれば、2つのアプローチの実行計画を比較して、あなたの元のアプローチは受け入れられます。 –

0

はこれを使用してみてください:

select * 
from reino r 
join especie e on (r.rnombre = e.ereino) 
join familia f on (f.freino = e.ereino and f.fnombre = e.efamilia) 

それはあなたがテーブルespecieにefamiliaとenombreを入れ替えること、だろうか?

+0

私は内部結合を探していません、とにかくありがとうございます。 – Roger

2

場合、このことができます:

リレーショナル

が話し、散弾銃の結婚のようなもの[OUTER JOINがある]:の種類にそれ 力テーブル組合 - はい、私は労働組合を意味しています、参加-さえない を問題のテーブルが通常の必要条件に合致しない場合は、 のユニオン用です。実際には、ユニオンを実行する前にどちらかのテーブルをヌルでパディングすることにより、 が通常の要件に準拠します。しかし、パディングが、この例のように、適切な値NULL値の代わりに で行われるべきではありません、なぜ何の 理由があります:

SELECT SNO , COALESCE (PNO , 'nil') AS PNO 
FROM S NATURAL LEFT OUTER JOIN SP 

出典:

SELECT SNO , PNO 
FROM SP 
UNION 
SELECT SNO , 'nil' AS PNO 
FROM S 
WHERE SNO NOT IN (SELECT SNO FROM SP) 

上記は以下と等価ではありません SQL and Relational Theory: How to Write Accurate SQL Code By C. J. Date

1

あなたが持っているものからわずかな変更だけでクエリを書き直したい場合は、LEFTに参加してFULLに参加してください。あなたはさらにON状態から冗長な括弧とr.rnombre = f.freinoを削除することができます。

select * 
from reino r 
    full join      --- instead of LEFT JOIN 
     familia f    
     right join especie e 
      on f.fnombre = e.efamilia 
      and f.freino = e.ereino 
     on r.rnombre = e.ereino; 
           ---removed the: r.rnombre = f.freino  
+0

私は最高の結果を望んでいますが、私はそれを書き直さなければならないかどうか気にしません。データベースには何が最適なのですか? – Roger

+0

種を持つ家族だけが必要なので、 'r.rnombre = f.freino'は必要ありません。 Join構造体から括弧を削除することは、DBMSに応じて影響を受ける可能性があります(Oracleの専門家はいません)。 –

+0

ほんのわずかです。このクエリー(そして、マイケルによって受け入れられたもの)には、王国を持つ家系は含まれません(しかし種はありません)。 –

関連する問題