You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQL如何查询父表中存在子表对应关联记录的数据行

查询父表与子表关联数据方案

表结构参考

父表 parent

piddescription
1hi
2hello
3haha
4huhu
5hoho

子表 child

子表通过pid字段关联父表主键pid,存储父表记录的关联子数据:

pidcid
12
13
35

示例数据中,pid=1关联2条子记录,pid=3关联1条子记录,其余pid无对应子记录。

不同场景的SQL写法

场景1:仅返回有子表对应记录的父表行

只需要返回存在子表关联的父数据,用INNER JOIN内连接或EXISTS子查询均可,两种写法执行效率接近,可根据实际场景选择。

写法1:INNER JOIN 内连接

内连接会自动过滤无匹配子记录的父行,注意加DISTINCT去重,避免单父行对应多子记录时返回重复父数据:

SELECT DISTINCT p.*
FROM parent p
INNER JOIN child c ON p.pid = c.pid;

如果需要同时返回子表字段,去掉DISTINCT,补充要查询的子表字段即可:

SELECT p.*, c.cid
FROM parent p
INNER JOIN child c ON p.pid = c.pid;

写法2:EXISTS 子查询

无需额外去重,逻辑更直观,只要子表存在对应pid的记录就返回父行:

SELECT p.*
FROM parent p
WHERE EXISTS (
    SELECT 1 FROM child c WHERE c.pid = p.pid
);

以上写法返回结果为pid=1、pid=3两条父表记录。

场景2:返回全部父表行,无对应子记录时仅返回父表数据

用LEFT JOIN左连接实现,左连接会保留父表所有行,子表无匹配时子表字段返回NULL:

SELECT p.*, c.cid
FROM parent p
LEFT JOIN child c ON p.pid = c.pid;

查询结果如下:

piddescriptioncid
1hi2
1hi3
2helloNULL
3haha5
4huhuNULL
5hohoNULL

如果不需要重复展示父行,只想聚合展示对应子记录id,可以用GROUP_CONCAT(MySQL)或对应数据库的聚合函数处理:

SELECT p.*, GROUP_CONCAT(c.cid) AS relate_cid
FROM parent p
LEFT JOIN child c ON p.pid = c.pid
GROUP BY p.pid;

场景3:按父表条件搜索,返回匹配行+关联的父表行

对应你举例的description = 'hi'时返回pid=1、2、3的需求,本质是返回匹配搜索条件的父行,以及这些父行在子表中关联cid对应的父表行,用UNION合并结果即可:

-- 查询匹配搜索条件的父行
SELECT p.* FROM parent p WHERE p.description = 'hi'
UNION
-- 查询匹配行在子表中关联cid对应的父行
SELECT p2.*
FROM parent p
INNER JOIN child c ON p.pid = c.pid
INNER JOIN parent p2 ON c.cid = p2.pid
WHERE p.description = 'hi';

执行后刚好返回pid=1、2、3三条父表记录。如果需要递归查询多层关联(比如pid=3关联的cid=5对应父行也要返回),可以用对应数据库支持的递归CTE语法(MySQL 8.0+、PostgreSQL等支持WITH RECURSIVE)调整实现。
如果某个pid在子表中无对应记录,UNION的第二部分查不到关联数据,只会返回第一部分匹配的父行本身,符合需求。

内容的提问来源于stack exchange,提问作者Crazy9

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.30 18:31:02