為什麼聚集函式不能出現在where子句中
阿新 • • 發佈:2019-02-16
這是一個很有意思的問題,仔細地想一下其實很有道理。我們知道,聚集函式也叫列函式,它們都是基於整列資料進行計算的,而where子句則是對資料行進行過濾的,在篩選過程中依賴“基於已經篩選完畢的資料得出的計算結果”是一種悖論,這是行不通的。更簡單地說,因為聚集函式要對全列資料時行計算,因而使用它的前提是:結果集已經確定!而where子句還處於“確定”結果集的過程中,因而不能使用聚集函式。與where子句不能出現聚集函式正相反的是,我們幾乎看不到不使用聚集函式的having子句。為什麼?因為在水平方向上根據外部指定條件的篩選(也就是對行的篩選),where子句可以獨立完成,剩下的往往都是需要根據結果集自身的統計資料進一步篩選了,這時,幾乎都需要通過having子句配合聚集函式來完成。
另外,對於having子句再多說一點:沒有使用group by而直接使用having子句的例子是不太多見,因為如果沒有group by,那麼整個結果集就是一個分組,但是這種例子也不是沒有,比如當我們需要對“現有的”整個結果集進行“二次篩選”時,就會直接使用having子句了。例如:
查詢一個Forum最新的Post的SQL為:
selectp.*fromForumfleftjoinThreadtonf.id=t.forumIdleftjoinPostpont.id=p.threadIdwheref.id=2havingmax(p.creationTime);