2011-12-28 76 views
1

所以這裏有一點關於系統的背景知識。用戶的戰鬥和勝利者是贏得最多輪次的人。我需要幫助可能加入三張桌子。我有表user之一,它存儲用戶信息。表match存儲匹配信息。表rounds其中每場比賽存儲每場比賽的勝者,所以如果一場比賽有5場比賽,那麼表rounds將有五場比賽並記錄每場比賽的勝者。需要複雜查詢的指導

下面是一些示例數據: 表user: (userid是主鍵)

userid username 
----------------- 
    1  Kevin 
    2  Sam 
    3  Steve 
    4  Matt 

match: (id是主鍵challengerchallenged均爲外鍵user.userid。)

id challenger challenged rounds 
----------------------------------- 
1  2   3   3 
2  1   2   1 
3  2   3   3 
4  2   4   1 

rounds : (所有字段都是主鍵。 id是外鍵match.idwinner是外鍵user.userid

id round winner 
------------------ 
1 1  2 
1 2  2 
1 3  3 
2 1  1 
3 1  2 
3 2  3 
3 3  2 
4 1  4 

我試圖建立一個查詢,將輸出下面的結果:

winner won loser won 
------------------------ 
Sam  2 Steve 1 
Kevin 1 Sam  0 
Sam  2 Steve 1 
Matt 1 Sam  0 

上述結果顯示贏家每場比賽的失敗者。 won字段顯示分別獲勝者和失敗者獲勝的比賽數。

有誰知道我可以如何建立上述查詢?

+0

而且,這裏重要的是,我認爲,如果他們配合會發生什麼?或者我們可以假設總會有奇數輪次? – Compeek 2011-12-28 07:58:26

+0

是的,總是有一個奇數 – user962449 2011-12-28 08:13:27

+0

我認爲你應該考慮在他們發生時確定勝利並將結果存儲在每場比賽的排中。因此,添加另一個字段以匹配被叫方贏家,並在匹配結束後儘快填入用戶的ID。與通過巨大的查詢來計算勝利相比,您可以節省大量開銷,就像在每次您需要結果時看到的一些答案中一樣。另外,這種方式更簡單。如果這對您的項目是可行的,我覺得這是一個更好的方法。 – Compeek 2011-12-28 16:32:47

回答

1
select 
    case when w1 > w2 then u1 else u2 end as winner, 
    case when w1 > w2 then w1 else w2 end as won, 
    case when w1 > w2 then u2 else u1 end as loser, 
    case when w1 > w2 then w2 else w1 end as won 
from (
    select m.id, u1.username as u1, u2.username as u2, 
     count(r1.winner) as w1, 
     count(r2.winner) as w2 
    from match m 
    join user u1 on m.challenger = u1.userid 
    join user u2 on m.challenged = u2.userid 
    join rounds r on r.id = m.id 
    left join rounds r1 on r.id = r1.id and r.round = r1.round and r1.winner = u1.userid 
    left join rounds r2 on r.id = r2.id and r.round = r2.round and r2.winner = u2.userid 
    group by m.id, u1.username, u2.username 
) t 

它依賴於(Problems with NULL Values):

骨料(摘要)功能,諸如COUNT(),MIN()和SUM()忽略NULL值

這裏是一個優點。

0

嘗試:

select match_id, 
     case when challenger_wins > challenged_wins 
      then challenger_name else challenged_name end) winner, 
     case when challenger_wins > challenged_wins 
      then challenger_wins else challenged_wins end) winner_won, 
     case when challenger_wins < challenged_wins 
      then challenger_name else challenged_name end) loser, 
     case when challenger_wins < challenged_wins 
      then challenger_wins else challenged_wins end) loser_won 
from 
(select m.id match_id, 
     max(case when u.userid = m.challenger 
       then u.username end) challenger_name, 
     sum(case when u.userid = m.challenger 
       then r.wins else 0 end) challenger_wins, 
     max(case when u.userid = m.challenged 
       then u.username end) challenged_name, 
     sum(case when u.userid = m.challenged 
       then r.wins else 0 end) challenged_wins 
from match m 
join user u on u.userid in (m.challenger, m.challenged) 
left join 
(select id, winner, count(*) wins 
    from round 
    group by id, winner) r 
on m.id = r.id and u.userid = r.winner 
group by m.id) v 
0

嘗試這一個 -

SELECT 
    IF(won1 >= won2, username1, username2) winner, 
    IF(won1 >= won2, won1, won2) won, 
    IF(won1 < won2, username1, username2) loser, 
    IF(won1 < won2, won1, won2) won 
FROM (
    SELECT u1.username username1, u2.username username2, COALESCE(r1.rounds, 0) won1, COALESCE(r2.rounds, 0) won2 FROM `match` m 
    JOIN user u1 
     ON u1.userid = m.challenger 
    JOIN user u2 
     ON u2.userid = m.challenged 
    LEFT JOIN (SELECT id, COUNT(round) rounds, winner FROM rounds GROUP BY id, winner) r1 
     ON r1.id = m.id AND r1.winner = u1.userid 
    LEFT JOIN (SELECT id, COUNT(round) rounds, winner FROM rounds GROUP BY id, winner) r2 
     ON r2.id = m.id AND r2.winner = u2.userid 
) t