SQL: 改进 Select 查询
SQL: Improve Select Query
我有理由相信这段代码可以做得更好,并且可能会从查询开始做更多的工作?
我会试着解释一下。
我数据库中的每一行都有一个 exercise
的 1、2 或 3 值,然后还有一个数字 rep
,它可以是任何数字,但在这段代码中我选择只关心 1-12,所以此代码选择具有最高值 kilograms
的行(这是一列,每行都有一个值),其中 exercise
为 1,rep
是 1,然后是 2 和 3 等等,直到 12,然后将 exercise
更改为 2,然后再次从 1-12 选择最上面的 kilograms
行。
这有意义吗?
for (var i = 1; i <= 3; i++) {
for (var ii = 1; ii <= 12; ii++) {
var getPR = "SELECT top 1 kg, rep, date FROM Test WHERE exerVariName = 'Comp' AND exercise = @0 AND rep = @1 order by kg desc";
db.Execute(getPR, i, ii);
foreach (var get in db.Query(getPR, i, ii)) {
DateTime Date = get.Date;
var finalDate = Date.ToString("MMM d, yyyy");
var weight = get.kg + "kg";
var reps = "x " + get.rep;
<a>@weight @reps - @finalDate</a>
<br>
}
}
}
我使用 SQL Server Compact,它不是 MVC 项目。
SELECT kg, rep, date, exercise, rep FROM Test test1 WHERE rep = (SELECT TOP 1 test2.rep FROM Test test2 WHERE test2.exercise = test1.exercise AND test2.rep = test1.rep ORDER BY kg DESC) GROUP BY exercise, rep
遍历这些结果并显示它们。
您可以 select 使用 Group By
和 MAX
聚合函数仅通过一次查询就可以查看您感兴趣的所有行。
SELECT t.kg, t.rep, t.date
FROM Test t
INNER JOIN
(SELECT MAX(kg) as kg, exercise, rep
FROM Test
WHERE exerVariName = 'Comp'
GROUP BY exercise, rep) i
ON t.exercise = i.exercise AND t.rep = i.rep AND t.kg = i.kg
WHERE t.exerVariName = 'Comp'
内部查询只执行一次。它找到一个组标识符 (exercise, rep)
元组和相应的最大 kg
组值。
然后将内部查询与 Test
table 连接以获得 "content" 行(在您的情况下只有一个附加字段 date
)。
整体性能是最佳的。
您只需迭代此查询的结果。
见this topic。
编辑:
排除具有相同 kg
的多个 (rep, exercise)
记录(与 OP 循环的结果几乎相同)
SELECT kg, rep, exercise, MAX(date)
FROM
(SELECT t.kg, t.rep, t.exercise, t.date
FROM Test t
INNER JOIN
(SELECT MAX(kg) as kg, exercise, rep
FROM Test
WHERE exerVariName = 'Comp'
GROUP BY exercise, rep) i
ON t.exercise = i.exercise AND t.rep = i.rep AND t.kg = i.kg
WHERE t.exerVariName = 'Comp') t
GROUP BY t.kg, t.rep, t.exercise
我有理由相信这段代码可以做得更好,并且可能会从查询开始做更多的工作?
我会试着解释一下。
我数据库中的每一行都有一个 exercise
的 1、2 或 3 值,然后还有一个数字 rep
,它可以是任何数字,但在这段代码中我选择只关心 1-12,所以此代码选择具有最高值 kilograms
的行(这是一列,每行都有一个值),其中 exercise
为 1,rep
是 1,然后是 2 和 3 等等,直到 12,然后将 exercise
更改为 2,然后再次从 1-12 选择最上面的 kilograms
行。
这有意义吗?
for (var i = 1; i <= 3; i++) {
for (var ii = 1; ii <= 12; ii++) {
var getPR = "SELECT top 1 kg, rep, date FROM Test WHERE exerVariName = 'Comp' AND exercise = @0 AND rep = @1 order by kg desc";
db.Execute(getPR, i, ii);
foreach (var get in db.Query(getPR, i, ii)) {
DateTime Date = get.Date;
var finalDate = Date.ToString("MMM d, yyyy");
var weight = get.kg + "kg";
var reps = "x " + get.rep;
<a>@weight @reps - @finalDate</a>
<br>
}
}
}
我使用 SQL Server Compact,它不是 MVC 项目。
SELECT kg, rep, date, exercise, rep FROM Test test1 WHERE rep = (SELECT TOP 1 test2.rep FROM Test test2 WHERE test2.exercise = test1.exercise AND test2.rep = test1.rep ORDER BY kg DESC) GROUP BY exercise, rep
遍历这些结果并显示它们。
您可以 select 使用 Group By
和 MAX
聚合函数仅通过一次查询就可以查看您感兴趣的所有行。
SELECT t.kg, t.rep, t.date
FROM Test t
INNER JOIN
(SELECT MAX(kg) as kg, exercise, rep
FROM Test
WHERE exerVariName = 'Comp'
GROUP BY exercise, rep) i
ON t.exercise = i.exercise AND t.rep = i.rep AND t.kg = i.kg
WHERE t.exerVariName = 'Comp'
内部查询只执行一次。它找到一个组标识符 (exercise, rep)
元组和相应的最大 kg
组值。
然后将内部查询与 Test
table 连接以获得 "content" 行(在您的情况下只有一个附加字段 date
)。
整体性能是最佳的。
您只需迭代此查询的结果。
见this topic。
编辑:
排除具有相同 kg
的多个 (rep, exercise)
记录(与 OP 循环的结果几乎相同)
SELECT kg, rep, exercise, MAX(date)
FROM
(SELECT t.kg, t.rep, t.exercise, t.date
FROM Test t
INNER JOIN
(SELECT MAX(kg) as kg, exercise, rep
FROM Test
WHERE exerVariName = 'Comp'
GROUP BY exercise, rep) i
ON t.exercise = i.exercise AND t.rep = i.rep AND t.kg = i.kg
WHERE t.exerVariName = 'Comp') t
GROUP BY t.kg, t.rep, t.exercise