所以我有一个查询,它将获取有关不可见项的匹配行的所有信息。
现在在while循环内部,我不得不使用选择计数查询来计算每个用户拥有多少不可见的项目,如果循环中有太多结果,则需要花费太多时间。
有没有一种方法可以查询它而不在while循环内运行选择查询?
例如:
SELECT categories.name,
quality.name,
users.regdate,
categories.name,
items.name,
items.visible,
items.owner,
users.username
FROM items
LEFT JOIN users ON items.owner = users.id
LEFT JOIN categories ON items.category = categories.id
LEFT JOIN quality on items.category_quality = quality.id
WHERE items.visible = 'no'
现在进入while循环以获取项目数,我不得不查询
while($row = mysqli_fetch_assoc($sql))
{
$all_items_by_user = "SELECT COUNT(items.name)
FROM items
WHERE items.owner = ".$row['owner']."";
$visible_items_by_user = "SELECT COUNT(items.name)
FROM items
WHERE items.owner = ".$row['owner']." AND items.visible = 'yes'";
// rest of code here.
// when there are 200 items in loop executing time goes crazy
// (6+ secs, where with 1 item it's around 0.05)
}
编辑示例:
有人要求看看最终的代码是什么,我会尽力而为。
忽略左联接,因为这不是相对的,我只是从整个查询中添加了这些联接。
Id | item name | owner | Visible
1 | Item 1 | 2 | no
2 | Item 2 | 2 | yes
3 | Item 3 | 2 | no
4 | Item 4 | 2 | no
5 | Item 5 | 2 | no
6 | Item 6 | 3 | no
7 | Item 7 | 3 | no
8 | Item 8 | 3 | no
9 | Item 9 | 4 | no
10 | Item 10 | 4 | no
在每个用户的while循环中,它应该计算用户拥有多少行。
例如: 用户2总共拥有5行,隐藏了4行,($ all_items_by_user将计算所有内容,而$ visible_items_by_user将仅计算1) 用户3拥有3行, 用户4拥有2行。
如何对每个用户的项目进行计数,因为如果我在while循环之外进行操作,它将仅对第一个用户计数,而不对每个用户计数。
最终结果应该是
while($row = mysqli_fetch_assoc($sql))
{
$all_items_by_user = "SELECT COUNT(items.name)
FROM items
WHERE items.owner = ".$row['owner']."";
$visible_items_by_user = "SELECT COUNT(items.name)
FROM items
WHERE items.owner = ".$row['owner']." AND items.visible = 'yes'";
echo $row['owner'] . "(Visible items: number | All items: number";
// Output: 2 (Visible items: 1 | All items: 5)
}
答案 0 :(得分:0)
您可以避免使用合并结果子查询的联接的循环查询
SELECT categories.name,
quality.name,
users.regdate,
categories.name,
items.name,
items.visible,
items.owner,
users.username,
ifnull(t.count_name,0),
ifnull(t.count_visible_name,0)
FROM items
LEFT JOIN users ON items.owner = users.id
LEFT JOIN categories ON items.category = categories.id
LEFT JOIN quality on items.category_quality = quality.id
LEFT JOIN (
select items.owner
, COUNT(items.name) count_name
, sum( case when items.visible = 'yes' AND item.name is not null
then 1 else 0 end) count_visible_name
from items
group by items.owner
) t on t.owner = items.owner
确保您具有正确的综合索引
on table items column(owner, category, category_quality)
答案 1 :(得分:0)
这假设您仅关心每个用户的计数,并且不关心任何项目的特定信息
SELECT items.owner,
COUNT(items.name) AS itemCount,
SUM( CASE WHEN items.visible = 'yes' AND item.name IS NOT NULL
THEN 1 ELSE 0 END) AS visibleCount
FROM items
GROUP BY items.owner
然后,您只需遍历每一行,即可为您提供该用户,该用户的总计数以及该用户的可见计数。