2017-07-01 12 views
0

私はデータベースで最終試験を受けています。サンプルのいくつかの問題を解決していたので、いくつか問題が発生しました。SUMのHAVING + MAXを使用したSQL - INTERECTECT

私は2つのテーブルの間に多対多の関係を持っています。私がしなければならない何

Player     PlayerTournament    Tournament 
-------     --------------------   ------------------- 
pk id_player    fk id_player     pk id_tournament 
name      fk id_tournament    name 
rank      year       city 
country     victories      court_surface 
                 tournament_type 

は次のとおりです。

1)。 2016年に粘土トーナメントで少なくとも1試合に勝ったが、どんな芝生大会にも参加しなかった選手(名前と国)を記載してください。

2)。最大の勝利数を持つ選手(名前、国、勝利の総数)を列挙してください。

私はこのような何かを考えていた:

1. SELECT P.NAME, P.COUNTRY 
FROM Player P INNER JOIN PlayerTournament PT 
ON P.ID_PLAYER= PT.ID_PLAYER 
INNER JOIN Tournament T 
ON T.ID_TOURNAMENT= PT.ID_TOURNAMENT 
WHERE T.COURT_SURFACE="clay" 
GROUP BY (something) 
HAVING SUM(PT.VICTORIES)>=1 
INTERSECT 
(same select and inner joins) 
WHERE T.COURT_SURFACE="grass" 
GROUP BY (something) 
HAVING COUNT(ID_PLAYER)=0 

2.SELECT P.NAME, P.COUNTRY, SUM(PT.VICTORIES) 
FROM Player P INNER JOIN PlayerTournament PT 
ON P.ID_PLAYER= PT.ID_PLAYER 
GROUP BY ... 
HAVING sum of victories = max sum of victories 

私は問題を考えた方法が正しいかどうかはわからない、私は「持つ」の文を支援する必要があります。

答えて

0

Q1:INTERSECTは動作しません。COUNT(ID_PLAYER)は決してNULLになりません。 HAVINGなしでEXCEPTに切り替える必要があります。

SELECT P.NAME, P.COUNTRY 
FROM Player P INNER JOIN PlayerTournament PT 
ON P.ID_PLAYER= PT.ID_PLAYER 
INNER JOIN Tournament T 
ON T.ID_TOURNAMENT= PT.ID_TOURNAMENT 
WHERE T.COURT_SURFACE IN ('clay', 'grass') 
GROUP BY (something) 
HAVING SUM(CASE WHEN T.COURT_SURFACE = 'clay' THEN PT.VICTORIES END)>=1 
AND COUNT(CASE WHEN T.COURT_SURFACE = 'grass' THEN PT.ID_PLAYER END)=0 

Q2:

クエリのこのタイプのための別の標準液は、(異なる条件で同じ選択)両方の条件が異なる場合に移動さ条件付き集約を利用してこれが最良のを求めるように見えます国ごとのプレーヤーがありますが、ネストされた集約はまれにしか許可されないため、直接書くことはできません。

WITH cte AS 
(
    SELECT P.NAME, P.COUNTRY, SUM(PT.VICTORIES) AS sumVic, 
     MAX(SUM(PT.VICTORIES)) OVER (PARTITION BY P.COUNTRY) AS maxVic 
    FROM Player P INNER JOIN PlayerTournament PT 
    ON P.ID_PLAYER= PT.ID_PLAYER 
    GROUP BY ... 
) 
SELECT * 
FROM cte AS t1 
WHERE sumVic = maxVic 
:あなたは同じレベルでMAX-計算を行うことができますより近代的な ウィンドウ表示集計関数を使用して

WITH cte AS 
(
    SELECT P.NAME, P.COUNTRY, SUM(PT.VICTORIES) AS sumVic 
    FROM Player P INNER JOIN PlayerTournament PT 
    ON P.ID_PLAYER= PT.ID_PLAYER 
    GROUP BY ... 
) 
SELECT * 
FROM cte AS t1 
WHERE sumVic = 
(SELECT MAX(sumVic) 
    FROM cte AS t2 
    WHERE t1.ID_PLAYER = t2.ID_PLAYER 
) 

:あなたは代わりに相関サブクエリを使用することができます