Php 左连接不太起作用

Php 左连接不太起作用,php,mysql,join,left-join,Php,Mysql,Join,Left Join,我有两个表:users和changes。我希望跟踪每个用户所做更改的数量。目前,我正在使用两个单独的语句结合PHP来完成这项工作: // Get all users $stmt = GlobalContainer::$dbh->prepare("SELECT id, username, realname FROM users ORDER BY role_id, realname"); $stmt->execute(); while

我有两个表:
users
changes
。我希望跟踪每个用户所做更改的数量。目前,我正在使用两个单独的语句结合PHP来完成这项工作:

// Get all users
$stmt = GlobalContainer::$dbh->prepare("SELECT 
        id, username, realname
    FROM 
        users
    ORDER BY role_id, realname");
$stmt->execute();
while ($user = $stmt->fetch()) {
    $users[$user['id']] = $user;
    $users[$user['id']]['changes'] = 0;
}

// Get number of changes for each user
$stmt = GlobalContainer::$dbh->prepare("SELECT COUNT(*) AS `count`, user_id 
    FROM 
        changes
    GROUP BY user_id");
$stmt->execute();
while ($changes = $stmt->fetch()) {
    $users[$changes['user_id']]['changes'] = $changes['count'];
}
这非常有效,但我认为如果我将其合并到一个查询中,会更整洁。这就是我所拥有的:

SELECT 
        users.id, users.username, users.realname, count(changes.user_id) as `count`
    FROM 
        users
    LEFT JOIN `changes` ON users.id = changes.user_id
    GROUP BY user_id
ORDER BY `count` ASC

但是,由于某些原因,它跳过了除一个用户之外的所有用户,并且更改为0,即使有多个用户。还有几个用户,每个用户有3个更改,并且它正确地显示了所有更改。如何使此查询正常工作,以便显示所有更改为0的用户?

将您的组更改为:

GROUP BY users.id

将您的组更改为:

GROUP BY users.id
您的计数会导致结果丢失,您可以将其嵌套在子查询中,以将其从左侧联接中排除,而左侧联接则只返回count(changes.user_id)所在的行,并将它们合并到一个记录中。如果使用子查询,则可以有效地获取changes.user\u id的计数,而不会影响左联接


您的计数会导致结果丢失,您可以将其嵌套在子查询中,以将其从左侧联接中排除,而左侧联接则只返回count(changes.user_id)所在的行,并将它们合并到一个记录中。如果使用子查询,您可以有效地获得changes.user\id的计数,而不会影响您的左连接。

看起来最近删除的答案是正确的。这是一个细分(和一个)。原始查询将
null
分组为单个结果。简单的答案是按一个不为null的值分组。这使最终查询如下所示:

SELECT 
        `users`.id, `users`.username, `users`.realname, count(changes.user_id) as `count`
    FROM 
        `users`
    LEFT JOIN `changes` ON users.id = changes.user_id
GROUP BY `users`.id;

看起来最近删除的答案是正确的。这是一个细分(和一个)。原始查询将
null
分组为单个结果。简单的答案是按一个不为null的值分组。这使最终查询如下所示:

SELECT 
        `users`.id, `users`.username, `users`.realname, count(changes.user_id) as `count`
    FROM 
        `users`
    LEFT JOIN `changes` ON users.id = changes.user_id
GROUP BY `users`.id;


你能发布数据吗?我不明白向用户显示0个更改是什么意思。如果该表中没有匹配项,则changes.user\u id将返回null。有时null会弄乱集合,如COUNT()。您可以尝试在COUNT()中用零替换null。这似乎可以解决此问题:
按用户分组。id
而不是
按更改分组。user\u id
。也许有人可以发布一个答案来解释原因,因为我真的不知道。这是对的吗?如果您的drop count、group by和REE execute()可以看到发生了什么,您是在分组nullsCan还是在发布数据?我不明白向用户显示0个更改是什么意思。如果该表中没有匹配项,则changes.user\u id将返回null。有时null会弄乱集合,如COUNT()。您可以尝试在COUNT()中用零替换null。这似乎可以解决此问题:
按用户分组。id
而不是
按更改分组。user\u id
。也许有人可以发布一个答案来解释原因,因为我真的不知道。这是对的吗?如果您的drop count和group by以及REE execute()可以看到发生了什么,那么如果您发现子查询返回相同的结果,那么您就是在分组NULL。我被纠正了。这实际上为每个用户返回相同的值。看起来像是所有行的总数。如果您发现子查询返回相同的结果,那么右语法使用第1行的“从用户向左加入对用户的更改。id=changes.user\u id group by us”将出现语法错误。我被纠正了。这实际上为每个用户返回相同的值。看起来像是所有行的总数。现在,右语法在第1行“from users left join changes on users.id=changes.user_id group by us”附近出现语法错误
MySQL服务器版本,因为左连接-更改表中的值可能为空,很好的回答。我希望我没有因为重新发布一个被否决的答案而冒犯任何人。我同意-在被否决的时候删除了我的答案,因为我认为我可能误读了这个问题。@dugas,我对你们两个都投了更高的票,但Jason的回答解释了为什么我需要这样做,所以我接受了他的回答。感谢你们两位。由于左连接,右侧-更改表中的值可能为空,很好地捕捉。我希望我没有因为重新发布投票结果被否决的答案而冒犯任何人。我同意-在投票结果被否决时删除了我的答案,以审查问题,因为我认为我可能误读了它。@dugas,我对你们两位投了更高的票,但杰森的回答解释了为什么我需要这么做,所以我接受了他的回答。谢谢你们两位。