2013-11-23 32 views
1

我有三個表。變化,討論和對話。每個討論都有一系列對話。每個對話都是關於一個改變。對話在討論中排在1-10位。你會最終得到這樣的事情:SUM的位置,使更高更好

Conversations{ 
    [ id: 1, discussion_id: 1, change_id 1, rank: 1 ], 
    [ id: 1, discussion_id: 1, change_id 3, rank: 3 ], 
    [ id: 1, discussion_id: 1, change_id 5, rank: 2 ], 
    [ id: 1, discussion_id: 1, change_id 2, rank: 4 ], 
    [ id: 1, discussion_id: 1, change_id 4, rank: 5 ], 
    [ id: 1, discussion_id: 2, change_id 3, rank: 1 ], 
    [ id: 1, discussion_id: 2, change_id 2, rank: 2 ], 
    [ id: 1, discussion_id: 2, change_id 4, rank: 5 ], 
    [ id: 1, discussion_id: 2, change_id 5, rank: 3 ], 
    [ id: 1, discussion_id: 2, change_id 1, rank: 4 ] 
    } 

我想找到最高的得分變化。當我想出這個查詢時,我想我已經這麼做了:

SELECT changes.*, SUM(conversations.rank) AS score FROM "changes" 
     INNER JOIN "conversations" ON "conversations"."change_id" = "changes"."id" 
     GROUP BY changes.id 

這就加起來了所有的等級。這意味着越低越好。然而,這個相當原始的解決方案有其缺陷:如果你給一個變化1和3的排名,它將以相同的分數結束,就像你用4排列一個變化一樣。

也許要解決這個問題,你可以使它所以越高越好:第一名= 5分,第二名= 4分等。我不知道如何實現這一點。它也可能不是最好的辦法。

Here你可以在上下文中找到一個SQL小提琴。只是一個參考:我正在積極創造記錄。我使用這個來生成查詢:

Change.select("changes.*, SUM(conversations.rank) as conversations_rank").group("changes.id").joins(:conversations) 
+0

而不是'總和'爲什麼不使用'平均'?然後按該列對結果進行排序。 – ethrbunny

+0

好的。我會放棄這一點。我仍然有興趣瞭解如何以排名的反面來做到這一點 - 用於學習目的。 – Jragon

+0

逆秩的問題正是你指出的:5 * 1的排名與1 * 5相同。 – ethrbunny

回答

0

我想出了兩種方法。兩者都非常簡單。我只是做一點點傻:)

第一個,也可能是最簡單的一個:

SELECT changes.name, SUM(11 - conversations.rank) as score FROM "changes" 
     INNER JOIN "conversations" 
     ON "conversations"."change_id" = "changes"."id" 
     GROUP BY changes.id 
     ORDER BY score desc 

簡單的數學誒。所以,如果conversations.rank = 1,那麼這將是10,因爲1減11爲10

也許是更好的方式來做到這一點是有另一個表:

CREATE TABLE ranks (
    rank INT UNSIGNED PRIMARY KEY, 
    value INT UNSIGNED 
); 

INSERT INTO ranks 
     VALUES (1, 5), 
       (2, 4), 
       (3, 3), 
       (4, 2), 
       (5, 1); 

然後做一個加入對話行列。排序:

SELECT changes.name, SUM(ranks.value) as score FROM "changes" 
     INNER JOIN "conversations" 
     ON conversations.change_id = changes.id 
     INNER JOIN "ranks" 
     ON conversations.rank = r.rank 
     GROUP BY changes.name; 

感謝您的所有幫助。