搞笑
left join(LEFT JOIN 一用就错?99% 的人踩过这个坑)
LEFT JOIN 一用就错?99% 的人踩过这个坑nerror="javascript:errorimg.call(this);">

早上刚开完站会,测试小姐姐又甩过来一条 SQL:

SELECt u.name, o.order_noFROM user AS uLEFT JOIN `order` AS o       ON u.id = o.user_idWHERe o.status = 1;

“不是说 LEFT JOIN 要保留所有用户吗?怎么结果少了一半?”

我扫了一眼,心里默默叹了口气:又是老问题——WHERe 里写了右表字段,把 LEFT JOIN 活生生写成了 INNER JOIN。

坑是怎么来的

LEFT JOIN 的语义是:左表全留,右表能匹配上就带过来,匹配不上就补 NULL。

但 WHERe 子句在 JOIN 之后执行。一旦你在 WHERe 里对右表字段做判断,比如:

WHERe o.status = 1

数据库必须先把 o.status 为 NULL 的行扔掉(NULL = 1 不成立),于是那些“没订单”的用户就被一并踢出去。
LEFT JOIN 的初心瞬间破功。

一句话记住规则

右表字段进 WHERe,LEFT 变 INNER;想留 NULL,条件写 ON。

改法:把条件挪到 ON 里

SELECt u.name, o.order_noFROM user AS uLEFT JOIN `order` AS o       ON u.id = o.user_id      AND o.status = 1;   -- 挪到这里

现在结果里:

  • 有订单且 status=1 → 订单号正常显示
  • 没订单或 status≠1 → 订单号显示 NULL,用户依旧存在

这才是 LEFT JOIN 该有的样子。

小结

  1. 检查所有 LEFT JOIN,看 WHERe 里有没有右表字段。
  2. 有就搬到 ON 里,除非你真的只想保留“匹配成功”的行——那不如直接用 INNER JOIN,语义更清晰。

写完这条提示,我顺手贴在团队 Wiki 最显眼的位置:

LEFT JOIN 里写右表条件,先问问自己:我到底想留 NULL 吗?


顶一下()     踩一下()

热门推荐

发表评论
0评