mysql实现层级查询,类似oracle里的connect by prior

cl000001 2014-04-10 12:21:27
举个简单例子:
select * from emp;


EMPNO ENAME JOB MGR HIREDATE SAL COMM DEPTNO
1 7369 SMITH CLERK 7902 1980-12-17 1800 20
2 7499 ALLEN SALESMAN 7698 1981-2-20 1600 300 30
3 7521 WARD SALESMAN 7698 1981-2-22 1250 500 30
4 7566 JONES MANAGER 7839 1981-4-2 2975 20
5 7654 MARTIN SALESMAN 7698 1981-9-28 1250 1400 30
6 7698 BLAKE MANAGER 7839 1981-5-1 2850 30
7 7782 CLARK MANAGER 7839 1981-6-9 2450 10
8 7788 SCOTT ANALYST 7566 1987-4-19 3000 20
9 7839 KING PRESIDENT 1981-11-17 5000 10
10 7844 TURNER SALESMAN 7698 1981-9-8 1500 0 30
11 7876 ADAMS CLERK 7788 1987-5-23 1100 20
12 7900 JAMES CLERK 7698 1981-12-3 950 30
13 7902 FORD ANALYST 7566 1981-12-3 3000 20
14 7934 MILLER CLERK 7782 1982-1-23 1300 10


现在想查询某些人及其所有下属员工信息,oracle中可以这样查询:
select * from emp
connect by prior empno=mgr
start with empno in (7902,7788)
;


1 7788 SCOTT ANALYST 7566 1987-4-19 3000 20
2 7876 ADAMS CLERK 7788 1987-5-23 1100 20
3 7902 FORD ANALYST 7566 1981-12-3 3000 20
4 7369 SMITH CLERK 7902 1980-12-17 1800 20

在mysql中有什么号方法替换吗,我在网上搜了比较多的是用函数:
CREATE FUNCTION getChildLst(rootId INT)
RETURNS varchar(1000) CHARSET utf8
BEGIN
DECLARE sTemp VARCHAR(1000);
DECLARE sTempChd VARCHAR(1000);

SET sTemp = '$';
SET sTempChd =cast(rootId as CHAR);

WHILE sTempChd is not null DO
SET sTemp = concat(sTemp,',',sTempChd);
SELECT group_concat(empno) INTO sTempChd FROM emp where FIND_IN_SET(mgr,sTempChd)>0;
END WHILE;
RETURN substr(sTemp,3);
END

然后用
select * from emp
where FIND_IN_SET(empno,concat(getChildLst(7902),',',getChildLst(7788)))
;

我在emp表empno字段建了索引,通过navicat for mysql 看上面的语句是全表扫描,没有走索引。

这种我试过一些数据量比较大的表,查询就很慢。

请教下大家是否有其他好的办法在mysql里实现上面的语句功能,另外还有个问题,就是这个函数一次只能返回一个父节点的所有子节点,如果我要查询的参数是多个,比如一个子查询:
select * from emp
connect by prior empno=mgr
start with empno in ( select empno from emp where deptno=30)
;

该怎么实现这种呢?
...全文
3186 2 打赏 收藏 转发到动态 举报
写回复
用AI写文章
2 条回复
切换为时间正序
请发表友善的回复…
发表回复
cutieagain 2016-01-05
  • 打赏
  • 举报
回复
select * from emp connect by prior empno=mgr start with empno in ( select empno from emp where deptno=30) ; 同求多了一个子查询该如何的这种方法。 我需要获取所有可以访问的子节点之后,根据子节点获取可以访问的所有父节点,子节点的个数有多个,所以用到in。
benluobo 2014-04-10
  • 打赏
  • 举报
回复
mysql没有这种函数,一般都是使用自定义函数编写,利用组合上层id,采用find_in_set函数实现层级查询

56,679

社区成员

发帖
与我相关
我的任务
社区描述
MySQL相关内容讨论专区
社区管理员
  • MySQL
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧