我正在创建一个测试系统,允许用户重新测试,直到他们通过。我想获得一个列表,对于给定的UserID,分配给他们的测试,他们得分低于传递(本例中为100%)。
我有以下表格:
(这里的所有内容都是为了简化而改编的,但它仍然有效)
Users
(Generic "users" table with UserID and Name, etc...)
Tests
+--------+----------+------------------+
| TestID | TestName | OtherTestColumns |
+--------+----------+------------------+
| 1 | Test 1 | Blah.... |
| 2 | Test 2 | Blah.... |
| 3 | Test 3 | Blah.... |
| 4 | Test 4 | Blah.... |
+--------+----------+------------------+
Users_Have_Tests
Users are assigned tests they must take with this table
+--------+--------+
| UserID | TestID |
+--------+--------+
| 1 | 1 |
| 1 | 2 |
| 1 | 3 |
| 2 | 1 |
| 2 | 2 |
| 2 | 3 |
+--------+--------+
TestResults
+--------+--------+------------+
| TestID | UserID | Percentage |
+--------+--------+------------+
| 1 | 1 | 75 |
| 1 | 1 | 100 |
| 2 | 1 | 80 |
| 2 | 1 | 100 |
| 1 | 2 | 100 |
| 2 | 2 | 75 |
+--------+--------+------------+
以下查询适用于我找出分配给用户的所有测试,但我想删除他们从此列表中传递的测试
SELECT DISTINCT
TestID,
TestName
FROM
`Users` AS u
RIGHT JOIN
`Users_have_Tests` AS ut
ON
u.UserID = ut.UserID
LEFT JOIN
`Tests` AS t
ON
ut.TestID = t.TestID
WHERE UserID = 1
我觉得我需要一个子查询。我想出了以下查询来查找用户每次测试的最大分数,但我不太确定如何将它们绑在一起。 (子查询对我来说很新,我仍然试图理解它们。)
SELECT DISTINCT
TestID,
MAX(Percentage)
FROM
`TestResults`
WHERE UserID = 1
GROUP BY TestID
我正在寻找的结果是:
UserID = 1
+--------+----------+
| TestID | TestName |
+--------+----------+
| 3 | Test 3 |
+--------+----------+
UserID = 2
+--------+----------+
| TestID | TestName |
+--------+----------+
| 2 | Test 2 |
| 3 | Test 3 |
+--------+----------+
我尝试了几种连接方式和条件,但我无法完全理解我在这里需要的东西。谷歌和StackOverflow让我失望;可能是因为我缺乏搜索内容的知识。
修改 以下是对我有用的:
SELECT DISTINCT t.TestID, t.TestName
FROM 'Users' AS u
RIGHT JOIN 'Users_have_Tests' AS ut
ON u.UserID = ut.UserID
LEFT JOIN 'Tests' AS t
ON ut.TestID = t.TestID
WHERE t.TestID NOT IN (
SELECT tr.TestID
FROM TestResults AS tr
WHERE tr.Percentage >= 100
AND tr.UserID = 2
)
AND u.UserID = 2
答案 0 :(得分:1)
您是否尝试过以下操作?
编辑我注意到你想看到最高分,所以我创建了一个子查询
编辑我忘记了分组。
此外,还需要在TestID和UserID上加入Test。
SELECT
TestID,
TestName,
HighestScore
FROM
`Users` AS u
RIGHT JOIN
`Users_have_Tests` AS ut
ON
u.UserID = ut.UserID
LEFT JOIN
( SELECT TestID, UserID, MAX(Percentage) AS HighestScore
FROM `Tests`
GROUP BY TestID, UserID
)AS t
ON
ut.TestID = t.TestID
AND ut.UserID = t.UserID
WHERE HighestScore < 100
GROUP BY TestID, TestName, HighestScore
答案 1 :(得分:1)
我想我现在明白你的意思,试一试:
SELECT DISTINCT
TestID,
TestName
FROM
`Users` AS u
RIGHT JOIN
`Users_have_Tests` AS ut
ON
u.UserID = ut.UserID
LEFT JOIN
`Tests` AS t
ON
ut.TestID = t.TestID
WHERE TestID NOT IN (SELECT TestID
FROM TestResults
Where Percentage = 100)
GROUP BY UserID
答案 2 :(得分:0)
我可能会遗漏一些东西,但为什么不运行以下查询并处理结果呢?
SELECT ut.UserId, ut.TestId, t.TestName
FROM `Users_Have_Tests` ut INNER JOIN `TestResults` r ON ut.TestId = r.TestId
INNER JOIN `Tests` t ON t.TestId = r.TestId
WHERE r.Percentage < 100
ORDER BY ut.UserId, ut.TestId;
如果您打算为单个用户执行此操作,只需添加WHERE子句条目以针对单个UserId值进行过滤。
答案 3 :(得分:0)
尝试有条款
之后
MAX(百分比)AS最高分数
小组之后说
拥有最高分数&lt; 100
然后用最低通过分数替换100 ..只返回没有超过最大条目的测试。
http://dev.mysql.com/doc/refman/5.0/en/group-by-handling.html