首页/数据/数据库速查/INNER JOIN 内连接
SQL 语法52 条

INNER JOIN 内连接

只返回两表都能匹配上的行;连接条件写在 ON(或等价的 WHERE),是最常用也最容易被优化器重排的连接类型。

数据库速查数据更新于 2026-10-13

INNER JOIN 是什么

INNER JOIN 是内连接,只返回两侧都能匹配上的行,本质是在两张表的组合里按连接条件取交集。MySQL 8.0 中 INNER JOIN、逗号连接与把条件写进 WHERE 是等价的,优化器自己决定谁做驱动表、按什么顺序连接,因此性能关键不在书写顺序,而在被驱动表的连接列上有没有索引。缺索引时被驱动表会被反复全表扫描,代价随驱动表行数成倍放大。

基本信息

用途取两表交集,横向拼接列
语法A INNER JOIN B ON 连接条件
等价写法FROM A, B WHERE A.列 = B.列
执行方式嵌套循环连接为主,无可用索引时 8.0.18 起可选哈希连接
关键前提连接列在两侧都要有索引,尤其被驱动表
条件分工连接条件写 ON,普通过滤条件写 WHERE

典型使用场景

  • 订单列表要展示下单人,用订单表连接用户表取昵称与等级
  • 报表按维表补全名称,例如渠道、地区、商品类目
  • 权限判断:连接角色授权表确认某个用户是否存在有效授权
  • 数据核对:找出同时存在于业务表与日志表中的记录
  • 多表明细导出,控制返回列避免生成过宽的结果集
  • 统计有订单的用户数,用于确认引用完整性

用法示例

用法示例
SELECT o.id, o.amount, u.name   # 只取需要的列
FROM orders o
INNER JOIN users u ON u.id = o.user_id   # 连接列两侧类型必须一致
WHERE o.status = 'paid'   # 普通过滤条件放在 WHERE
LIMIT 50;   # 明细查询务必限制返回行数

多表连接

多表连接
SELECT o.id, u.name, p.title
FROM orders o
JOIN users u ON u.id = o.user_id   # 行数少的表做驱动表通常更划算
JOIN products p ON p.id = o.product_id
WHERE o.created_at >= '2026-10-01';   # 过滤条件先收窄数据量

执行计划逐列读法

列含义正常与异常
id执行顺序编号,同号按从上到下执行顺序与书写顺序无关,别按语句顺序读
table当前访问的表排在前面的通常是驱动表
type访问类型const / eq_ref / ref 较好,ALL 表示全表扫描
possible_keys可用索引为空说明连接列上没有可用索引
key实际使用的索引为 NULL 时需要检查连接列的索引
rows预估扫描行数被驱动表数值很大说明连接在放大
Extra附加信息出现 Using join buffer 说明没走索引连接
EXPLAIN 里出现 Using join buffer 且预估行数很大,基本就是被驱动表的连接列缺索引:这时连接代价随驱动表行数成倍放大,补索引是最直接的优化。
MySQL 8.0.18 起,连接列没有可用索引时优化器可能选择哈希连接,性能优于嵌套循环扫描,但仍不如走索引的连接,不能当作不建索引的理由。
漏写连接条件会产生笛卡尔积,两表行数相乘,大表上足以瞬间打满临时空间与磁盘;多表查询写完后先确认返回行数是否符合预期,再交给业务使用。

连接性能检查清单

  • 被驱动表的连接列必须有索引,执行计划里的访问类型应落在等值或引用级别
  • 连接列两侧类型与字符集保持一致,避免隐式转换让索引失效
  • 先过滤再连接:把高选择性条件写进 WHERE,减少参与连接的行数
  • 只取需要的列,避免连接后大量回表读取宽列
  • 多表连接时用行数少的表做驱动表,减少内层循环次数
  • 不要在连接条件里对列做函数运算,表达式会阻断索引使用
连接结果行数异常放大时先检查是否漏写条件或存在多重匹配:一对多关系下同一条主记录会出现多次,业务侧应做去重或聚合,而不是靠限制返回行数掩盖问题。

易错点

  • 漏写 ON 条件形成笛卡尔积:十万行乘十万行直接压垮实例,多表查询先确认返回行数量级
  • 连接列的类型或字符集不一致:语句能跑,但隐式转换让索引失效退化为全表扫描,两侧定义必须统一
  • 把普通过滤条件全写进 ON:内连接下语义虽等价,但混写会降低可读性,后续改造成外连接时极易改错
  • 连接后不做聚合就返回明细:一对多关系把结果集放大数倍,接口返回重复行,前端出现重复展示
  • 只在主表建索引:连接条件两侧都要有索引,主表的索引对被驱动表的扫描毫无帮助

数据来源与参考

  • MySQL 8.0 Reference Manual: JOIN Clause

相关工具

​‌‌​​‌​​​‌‌​‌‌‌‌​‌‌​​​‌‌​‌‌‌​​‌‌​​‌​‌‌‌​​‌‌‌​​​‌​‌‌​‌​​‌​‌‌‌​​​‌​‌‌​‌​​‌​‌‌​​​‌‌​‌‌‌​‌​​​‌‌​‌‌‌‌​​‌​‌‌‌​​‌‌​​​‌‌​‌‌​‌‌‌‌​‌‌​‌‌​‌