SQL中无MERGE函数,其等价操作是JOIN:INNER JOIN取交集,LEFT/RIGHT JOIN主表全保留、另一侧补NULL,FULL OUTER JOIN取并集,CROSS JOIN为笛卡尔积。

SQL里没有merge函数,但JOIN就是它的等价实现
Python的pd.merge()本质是按键对齐两张表,SQL里完全对应的是JOIN操作。别被“merge”这个词带偏——它不是SQL标准语法,也不是某个数据库特有命令,所有主流SQL引擎(MySQL、PostgreSQL、SQLite、SQL Server)都用JOIN完成同样逻辑。
INNER JOIN:只保留两表都存在的匹配行
这是最常用、也最容易被默认当成“merge默认行为”的连接方式。如果你没指定类型,有些工具(比如某些BI平台自动生成SQL)可能默认用它,但标准SQL必须显式写明。
- 适用场景:查“用户有订单且订单已支付”的数据,排除无订单用户或无效订单
- 常见错误:误以为
INNER JOIN会补空值——它不会,不匹配的行直接丢弃 - 性能提示:数据库通常会对
ON字段自动走索引,但若连接条件含函数(如ON UPPER(a.name) = UPPER(b.name)),索引大概率失效
示例:
SELECT u.id, u.name, o.order_date FROM users u INNER JOIN orders o ON u.id = o.user_id;
LEFT JOIN和RIGHT JOIN:主表优先,另一侧补NULL
LEFT JOIN保留左表全部行,右表无匹配则填NULL;RIGHT JOIN反之。实际中RIGHT JOIN极少用——可读性差,且总能改写成LEFT JOIN(调换表顺序即可)。
让 macOS 自动化像说话一样简单 —— 用代码控制你的 Mac,无需学习 AppleScript 系统要求 macOS 14+ (Sonoma) Python 3.9+ 需要开启:辅助功能 + 屏幕录制权限
- 关键区别:连接方向决定哪张表是“主表”。
FROM a LEFT JOIN b中,a是主表,b是被挂载的附表 - 容易踩的坑:在
WHERE里对右表字段加非空判断(如WHERE b.status IS NOT NULL),会把LEFT效果变相转成INNER——因为NULL行被过滤掉了 - 替代方案:想保留左表+右表部分条件匹配?把条件移到
ON子句里,而不是WHERE
示例(正确保留所有用户,哪怕没订单):
SELECT u.name, o.order_date FROM users u LEFT JOIN orders o ON u.id = o.user_id AND o.status = 'paid';
FULL OUTER JOIN和CROSS JOIN:边界情况才用
FULL OUTER JOIN返回左右两表所有行,无匹配处填NULL;CROSS JOIN是笛卡尔积,每行配每行——结果行数=左行数×右行数。它们不像前三种那么高频,但一旦需要就不可替代。
立即学习“Python免费学习笔记(深入)”;
-
FULL OUTER JOIN在MySQL中不原生支持(需用LEFT JOIN + RIGHT JOIN + UNION模拟),PostgreSQL/SQL Server直接支持 -
CROSS JOIN常用于生成组合配置、时间维度展开(如“每个产品 × 每个月份”),但若表各1万行,结果就是1亿行——务必确认业务意图,加好LIMIT或提前过滤 - 注意:省略
JOIN关键字直接写FROM a, b等价于CROSS JOIN,但这种写法易被误读,建议显式写出
示例(生成2024年每月销售额模板):
SELECT p.product_name, m.month
FROM products p
CROSS JOIN (VALUES ('Jan'), ('Feb'), ('Mar')) AS m(month);
真正难的不是记住五种JOIN名称,而是每次写之前想清楚:我要保留哪张表的完整性?不匹配的记录是否允许丢失?连接条件是否隐含了业务过滤逻辑?这些判断比语法本身更影响结果正确性。

















