对于每个玩家,在“表现合理”查询中显示他们当前的游戏和邀请。
| PLAYERS | | GAMES |
| ID | Name | | ID | Name |
|------|------| |-----|----------|
| 1 | Abby | | 1 | Baccarat |
| 2 | Billy| | 2 | BlackJack|
| 3 | Cary | | 3 | Craps |
| 4 | Dolly| | 4 | Roulette |
| 5 | Eddy |
通过列表邀请玩家参加游戏。该列表可以随时更改,因此玩家可能会被邀请参加游戏,然后从以下列表中的游戏中删除:
|LIST| | INVITE |
| ID | | ID | LIST | PLAYER | GAME |
|----| |----|------|--------|------|
| 1 | | 1 | 1 | 1 | 2 |
| 2 | | 2 | 1 | 2 | 2 |
| 3 | | 3 | 1 | 3 | 2 |
| 4 | | 4 | 1 | 4 | 2 |
| 5 | | 5 | 1 | 5 | 2 |
| 6 | | 6 | 2 | 1 | 2 |
| 7 | | 7 | 2 | 2 | 2 |
| 8 | | 8 | 2 | 3 | 2 |
| 9 | | 9 | 2 | 4 | 2 |
| 10 | 3 | 1 | 4 |
| 11 | 3 | 2 | 4 |
| 12 | 3 | 5 | 4 |
| 13 | 4 | 4 | 1 |
| 14 | 4 | 5 | 1 |
| 15 | 5 | 1 | 4 |
| 16 | 5 | 4 | 4 |
| 17 | 5 | 5 | 4 |
| 18 | 6 | 4 | 4 |
| 19 | 6 | 5 | 4 |
| 20 | 7 | 1 | 4 |
| 21 | 7 | 2 | 4 |
| 22 | 7 | 3 | 4 |
| 23 | 7 | 4 | 4 |
| 24 | 7 | 5 | 4 |
| 25 | 8 | 1 | 3 |
| 26 | 8 | 2 | 3 |
| 27 | 8 | 3 | 3 |
| 28 | 8 | 4 | 3 |
在进行一轮游戏之前,列表可以更新零次或多次。游戏开始时,该回合标记为开始,完成时标记为结束。
| ROUND | |
| ID | Game | List | State |
|------|------|------|--------|
| 1 | 2 | 1 |FINISHED|
| 2 | 2 | 2 |FINISHED|
| 3 | 2 | 2 |STARTED |
| 4 | 4 | 3 |STARTED |
| 5 | 3 | 8 |STARTED |
玩家完成的游戏:
SELECT * FROM GAMES G
JOIN INVITE I ON I.GAME = G.ID
JOIN PLAYER P ON P.ID = I.PLAYER
JOIN ROUND R ON G.ID = R.GAME
WHERE R.STATE = 'FINISHED'
但我正在努力对当前游戏和邀请进行条件查询。我认为当前的游戏查询是:
SELECT * FROM GAMES G
JOIN INVITE I ON I.GAME = G.ID
JOIN PLAYER P ON P.ID = I.PLAYER
JOIN ROUND R ON G.ID = R.GAME
WHERE R.STATE = 'STARTED'
我认为邀请部分是:
SELECT * FROM GAMES G
JOIN INVITE I ON I.GAME = G.ID
JOIN PLAYER P ON P.ID = I.PLAYER
WHERE I.LIST = (
SELECT MAX(LL.ID)
FROM LIST LL
WHERE LL.GAME = G.ID
)
但我很难将这些结合起来,以及这是否是一个“性能合理”的解决方案。
期望的结果
列表执行以下操作:
回合执行以下操作:
每个参与者登录时,他们都会看到受邀并可能开始的游戏列表;当游戏进行时,他们可以看到游戏。游戏结束后,他们只有在最近的列表中被(重新)邀请才能看到游戏。单独的查询用于查看每个玩家所参加的已完成游戏。某些列表永远不会应用于一轮。
给定玩家ID,显示当前游戏和邀请游戏的列表。例如,对于 Abby,一旦创建了列表 #1,Abby 就会看到 BlackJack;当第一轮开始时,艾比看到了二十一点;创建列表 2 后,Abby 继续看到 BlackJack
虽然我发现它有点难以理解,但我已经可以说这么多了:邀请表看起来很糟糕,我认为它违反了数据库规范化规则。
似乎每个列表都指的是一款游戏。所以游戏ID应该是列表表中的属性,而不是邀请表中的属性,也不是回合表中的属性。
CREATE TABLE player (
id_player SERIAL PRIMARY KEY,
name VARCHAR(10)
);
CREATE TABLE game (
id_game SERIAL PRIMARY KEY,
name VARCHAR(10)
);
CREATE TABLE list (
id_list SERIAL PRIMARY KEY,
id_game INTEGER NOT NULL REFERENCES game
);
CREATE TABLE invite (
id_invite SERIAL PRIMARY KEY,
id_list INTEGER NOT NULL REFERENCES list,
id_player INTEGER NOT NULL REFERENCES player
);
CREATE TABLE round (
id_round SERIAL PRIMARY KEY,
id_list INTEGER NOT NULL REFERENCES list,
status VARCHAR(10)
);
现在,如果我理解正确的话,该列表将被解释为每场比赛的历史记录。因此,对于每款游戏,我们都会查看其最新列表,以了解当前邀请哪些玩家参加该游戏。
在你的例子中
其他列表只是历史,我们不必看。
现在您想要显示仍邀请玩家参加的所有游戏的所有回合。类似的东西
WITH
latest_lists AS
(
SELECT id_game, MAX(id_list) AS last_id_list
FROM list
GROUP BY id_game
)
SELECT p.name, r.id_round, g.name, r.status
FROM round r
JOIN latest_lists ll ON ll.last_id_list = r.id_list
JOIN game g ON g.id_game = ll.id_game
JOIN invite i ON i.id_list = ll.last_id_list
JOIN player p ON p.id_player = i.id_player
ORDER BY p.name, r.id_round;