2015-02-23 43 views
0

我有一個表中的兩列:按平均評分排序 - 如何加快速度?

rating_total integer 
rating_count integer 

rating_total是總房價的總和,並且等級數是多少總評級。我想按平均價格訂購:

ORDER BY (rating_total/rating_count) DESC, id ASC 

我應該爲average_rate創建單獨的列嗎?或者可以創建一些索引來加快速度?


我已經成功地創建索引這樣的:

CREATE INDEX "posts-avg-rating-index" 
ON "Posts" (("rating_total"::float/(CASE "rating_count" WHEN 0 THEN NULL ELSE "rating_count" END)) DESC NULLS LAST, id DESC);' 

這對於訂購這樣工作的:

ORDER BY (("rating_total"::float/(CASE "rating_count" WHEN 0 THEN NULL ELSE "rating_count" END)) DESC NULLS LAST, id DESC) 
+0

爲什麼不'AVG(等級)'(假設你有一個等級列)? – 2015-02-23 09:22:15

+1

你應該使用單獨的'列'或採取[看](http://stackoverflow.com/a/4068083/2749470)對這個答案 – 2015-02-23 09:22:21

+0

@JackManey我沒有執行任何分組,每一行已經計算出rating_total和rating_count 。 – user606521 2015-02-23 09:25:36

回答

2

你的問題產生了一些混亂,因爲 「平均評級」通常爲多行之間計算的值,這些行不能被索引。

在你的情況下,你顯然想要通過相同的行中的兩列的商來訂購,其恰好是「總計」和「計數」。對於這種情況,你可以有一個expression index,當然 - 你自己已經找到了一個。

您可以NULLIF簡化:

CREATE INDEX posts_avg_rating_index 
ON "Posts" (cast(rating_total AS float)/NULLIF(rating_count, 0) DESC NULLS LAST, id DESC); 

使用相同的表達您的查詢。

關於cast()語法速記name::type和表達指數:

而且還是用法律名稱。標識符中的破折號(-)在雙引號時是合法的,但只是要求麻煩。

+0

在表達式索引上使用物化視圖和索引或[觸發器更新]計算值列是否有令人信服的理由?似乎表達式索引需要在內部存儲結果.. – user2864740 2015-02-23 16:31:04

+1

@ user2864740:這是一個很好的問題。這兩種解決方案都有自己的成本,收益和副作用。請爲此詢問一個新的*問題*。評論不是這個地方。你可以隨時鏈接到這個問題的上下文。 – 2015-02-23 16:53:44