2016-06-10 51 views
1

我有兩個有效的查詢,仍然試圖更好地理解子查詢,但現在打牆。嘗試將總體Average添加到此SQL查詢中。

第一個代碼工作正常,並做我想要的。我只得到1-4下場比賽的比賽,並且我可以用AVG(togo)得到平均場數。

Select OffenseTeam, Avg(Togo) as YdsToGo,Down as Downtogo, Down = Case 
when Down =1 Then Count(Down) 
when Down =2 Then Count(Down) 
when Down =3 Then Count(Down) 
when Down =4 Then Count(Down) End 
From temp_NFL2015 
WHere ToGo <> 0 
Group By OffenseTeam, Down 
Order By OffenseTeam ASC, Downtogo ASC 

下一個查詢給了我整個聯盟的總體平均值,四條幹淨的線是這個查詢的結果。

Select Down, Avg(Togo) as YTG 
From Temp_NFL2015 
Where Togo<>0 
Group By Down 
Order By Down ASC 

現在,當我嘗試合併它們時,我失敗了。我與書的例子下面一起,這似乎是用來精確的格式,但它不能

Select OffenseTeam, Avg(Togo) as YTG,Down as Downtogo, Down = Case 
when Down =1 Then Count(Down) 
when Down =2 Then Count(Down) 
when Down =3 Then Count(Down) 
when Down =4 Then Count(Down) End 
     (Select Down, Avg(Togo) as YTG 
     From Temp_NFL2015 
     Where Togo<>0 
     Group By Down 
     Order By Down ASC) as LGAvg 
From temp_NFL2015 
WHere ToGo <> 0 
Group By OffenseTeam, Down 
Order By OffenseTeam ASC, Downtogo ASC 

回答

2

現在你在你的子查詢中選擇兩列,並試圖把它們合併到一列(Down, Avg(Togo) - >LGAvg

雖然我想建議JOIN,這裏有幾個選項可以讓你使用子查詢,因爲你正在學習這些。

一個,你可以使用一個臨時表,並加入:

Select Down, Avg(Togo) as YTG 
Into  #Temp 
From  Temp_NFL2015 
Where Togo<>0 
Group By Down 

然後主查詢:

(SELECT YTG 
FROM (Select Down, Avg(Togo) as YTG 
     From Temp_NFL2015 
     Where Togo<>0 
     Group By Down) avg 
WHERE avg.Down = nfl.Down) as LGAvg 

Select OffenseTeam, Avg(Togo) as YTG,Down as Downtogo, Down = Case 
when Down =1 Then Count(Down) 
when Down =2 Then Count(Down) 
when Down =3 Then Count(Down) 
when Down =4 Then Count(Down) End, 
     (Select YTG 
     From #TEMP t 
     Where t.down = nfl.down) as LGAvg 
From temp_NFL2015 nfl 
Where ToGo <> 0 
Group By OffenseTeam, Down 
Order By OffenseTeam ASC, Downtogo ASC 

兩個,你可以在你的子查詢使用嵌套查詢

整個查詢:

Select OffenseTeam, Avg(Togo) as YTG,Down as Downtogo, Down = Case 
    when Down =1 Then Count(Down) 
    when Down =2 Then Count(Down) 
    when Down =3 Then Count(Down) 
    when Down =4 Then Count(Down) End, 
    (SELECT YTG 
    FROM (Select Down, Avg(Togo) as YTG 
      From Temp_NFL2015 
      Where Togo<>0 
      Group By Down) avg 
    WHERE avg.Down = nfl.Down) as LGAvg 
From temp_NFL2015 nfl 
Where ToGo <> 0 
Group By OffenseTeam, Down 
Order By OffenseTeam ASC, Downtogo ASC 

然後有選項3,即將選項2的嵌套選擇邏輯放入JOIN,並在主查詢中簡單地選擇LGAvg。看起來像都鐸王朝你在那裏覆蓋。

編輯:附加說明

讓我們把你的前兩個查詢(簡體)的輸出並對其進行分析。

第一個查詢輸出是這樣的:

Team | Down | Count 
    A  1  18 
    A  2  15 
    A  3  13 
    A  4  11 
    B  1  19 
    B  2  16 
    B  3  13 
    B  4  10 

你的第二個輸出這樣的:

Down | LGAvg 
    1  18 
    2  13 
    3  11 
    4  9 

希望將LGAvg添加到第一個查詢。因爲我們想要使用子查詢,所以我們可以簡單地將查詢2複製到查詢1的SELECT語句中。這使我們向你是其中:

Select OffenseTeam, Avg(Togo) as YTG,Down as Downtogo, Down = Case 
when Down =1 Then Count(Down) 
when Down =2 Then Count(Down) 
when Down =3 Then Count(Down) 
when Down =4 Then Count(Down) End, 
     (Select Down, Avg(Togo) as YTG 
     From Temp_NFL2015 
     Where Togo<>0 
     Group By Down 
     Order By Down ASC) as LGAvg 
From temp_NFL2015 
WHere ToGo <> 0 
Group By OffenseTeam, Down 
Order By OffenseTeam ASC, Downtogo ASC 

但現在我們有幾個問題:

  • 我們選擇我們的子查詢(DownYTG)內2列。我們不能這樣做,因爲我們的子查詢的結果是通過在外部查詢一列代表(LGAvg
  • 我們仍然有我們的子查詢,這是不允許的ORDER BY而無論如何也不會一事無成
  • 我們需要提供一個關聯,它將定義我們希望內部查詢如何連接到外部查詢。 這是相同的概念ON子句中JOIN

首先,讓我們刪除ORDER BY

(Select Down, Avg(Togo) as YTG 
From Temp_NFL2015 
Where Togo<>0 
Group By Down) as LGAvg 

接下來,讓我們踏踏實實地選擇一列,YTG。我們必須使我們的當前查詢派生表,以便接着只選擇YTG

(SELECT YTG FROM (--Begin derived table 
(Select Down, Avg(Togo) as YTG 
From Temp_NFL2015 
Where Togo<>0 
Group By Down)) avgY --End derived table with an alias 

快速注此處使用avg作爲別名是不好的做法,我不應該做的是,爲確切的原因是爲什麼它讓你困惑。它看起來像AVG()函數,並使讀者更難以理解查詢。我將它改爲avgY作爲'平均碼',但您可以將其替換爲您想要的值。

現在我們只是錯過了我們的關聯。我們需要添加WHERE avgY.Down = nfl.down,因爲這就是我們希望行匹配的方式。我們做這種相關性派生表,這給我們留下了這樣的外

(SELECT YTG 
FROM (Select Down, Avg(Togo) as YTG 
     From Temp_NFL2015 
     Where Togo<>0 
     Group By Down) avgY 
WHERE avgY.Down = nfl.Down) as LGAvg --avgY and nfl are aliases for inner and outer queries 

希望這清除它。請記住,如果我們把這個膽量到一個臨時表(見這個答案的頂部),那麼我們可以簡單地引用了臨時表,這是很容易理解:

(Select YTG 
    From #TEMP avgY 
    Where avgY.down = nfl.down) as LGAvg 

我們要做而是在主查詢中包含子查詢的內容。爲了證明這一點,看看如果你把上面的字粘貼在#TEMP這個詞上,會發生什麼?

膽:

(Select Down, Avg(Togo) as YTG 
From Temp_NFL2015 
Where Togo<>0 
Group By Down) 
+0

非常完美,再次感謝您提供了一個有用的示例,第二個選項的「完整查詢」功能完美。再次,我會坐在這裏,試着理解到底發生了什麼。仍處於學習的開始階段,這有助於。 儘管在你的代碼中,你在該Group By Down行的結尾處有avg。以前從未見過。 然後下一行......「AVG」。而不是「AVG(」?然後「nfl。」? Group By Down)avg WHERE avg.Down = nfl.Down)as LGAvg – hitbid

+0

@hitbid總是樂於幫忙。對於SQL新手來說,你已經進入了一些相當先進的概念。保持!我將編輯一些關於子查詢如何工作的更多解釋。 –

+1

現在好了。派生表概念是有道理的,當你澄清別名時,我有我的「Oooooooooh」時刻。很棒的迴應,我非常感謝。 – hitbid

1

你希望將它們組合的方式還不是很清楚,但我的猜測是,你想參加兩個查詢的向下價值......如果是這樣,這是你怎麼做

Select OffenseTeam, Avg(l.Togo) as YTG,l.Down as Downtogo, Down = Case 
when l.Down =1 Then Count(l.Down) 
when l.Down =2 Then Count(l.Down) 
when l.Down =3 Then Count(l.Down) 
when l.Down =4 Then Count(l.Down) End 
From temp_NFL2015 l 
join 
(Select Down, Avg(Togo) as YTG 
     From temp_NFL2015 
     Where Togo<>0 
     Group By Down) as LGAvg on LGAvg.Down=l.Down 

WHere l.ToGo <> 0 
Group By l.OffenseTeam, l.Down 
Order By l.OffenseTeam ASC, l.Down ASC 
+0

感謝。下面的亞倫的「整個查詢」實際上正是我所需要的。 – hitbid