zoukankan      html  css  js  c++  java
  • 用mysql存储过程代替递归查询

    查询此表某个id=4028ab535e370cd7015e37835f52014b(公司1)下的所有数据

    正常情况下,我们采用递归算法查询,如下

    public void findCorpcompanyListByParentId(List<UapcompanyVo> vos,String parentId){
    		UapcompanyParam param = new UapcompanyParam();
    		param.setParentid(parentId);
    		List<Uapcompany> companyList = uapcompanyDao.finduapcompanyList(param);
    		UapcompanyVo uapcompanyVo = null;
    		for(Uapcompany uapcompany : companyList){
    			uapcompanyVo = new UapcompanyVo();
    			uapcompanyVo = new UapcompanyVo();
    			uapcompanyVo.setId(uapcompany.getId());
    			uapcompanyVo.setName(uapcompany.getName());
    			uapcompanyVo.setParentid(uapcompany.getParentid());
    			vos.add(uapcompanyVo);
    			this.findCorpcompanyListByParentId(vos, uapcompany.getParentid());
    		}
    }

    递归查询也能实现该需求,但是这样有两个缺点:一,性能很差 ,因为每递归一次至少调用一次数据链接;二,如果数据量很大的话,可能会导致溢出,当然可以修改虚拟机参数,不过这也是治标不治本的方法

    接下来,我们看一下存储过程实现查询:

    选择函数-->右键-->选择新建函数

    选择过程

    添加入参参数,如下图所示

    完成,如下图所示

    在begin end区域编写存储过程内容

    BEGIN
    	#声明一个flag变量,默认值为-99
    	DECLARE flag INT DEFAULT -99;
    	
    	#创建companyTempTabl_Qurey临时表
    	CREATE TEMPORARY TABLE IF NOT EXISTS companyTempTabl_Qurey (
    		id VARCHAR(32) NOT NULL,
    		`name` VARCHAR(100),
    		attr VARCHAR(30),
    		parentId VARCHAR(32)
    	);
    	TRUNCATE TABLE companyTempTabl_Qurey;
          #创建companyTempTabl_Result临时表
          CREATE TEMPORARY TABLE IF NOT EXISTS companyTempTabl_Result (
    		id VARCHAR (32) NOT NULL,
    		`name` VARCHAR (100),
    		attr VARCHAR (30),
    		parentId VARCHAR (32)
    	);
    	TRUNCATE TABLE companyTempTabl_Result;
    	
    	#根据参数 parentId 查询数据,并插入companyTempTabl_Qurey临时表
    	INSERT INTO companyTempTabl_Qurey (
    		id,
    		`name`,
    		attr,
    		parentId
    	) SELECT
    	uapcompany.id,
    	uapcompany.`name`,
    	uapcompany.attr,
    	uapcompany.parentId
    	FROM uapcompany 
    	WHERE uapcompany.parentId = `parentId`;
    	
          #根据参数 parentId 查询数据,并插入companyTempTabl_Result临时表
    	INSERT INTO companyTempTabl_Result (
    		id,
    		`name`,
    		attr,
    		parentId
    	) SELECT
    	uapcompany.id,
    	uapcompany.`name`,
    	uapcompany.attr,
    	uapcompany.parentId
    	FROM uapcompany 
    	WHERE uapcompany.parentId = `parentId`;
    	
    	#根据参数 parentId 统计查询总数,并赋值给变量flag
    	SELECT count(1) INTO flag 
    	FROM uapcompany 
    	WHERE uapcompany.parentId = `parentId`;
    	
    	#如果flag 大于 0,则进行循环
    	WHILE flag > 0 DO
    		#创建companyTempTabl_temp 临时表
    		CREATE TEMPORARY TABLE IF NOT EXISTS companyTempTabl_temp (
    			id VARCHAR (32) NOT NULL,
    			`name` VARCHAR (100),
    			attr VARCHAR (30),
    			parentId VARCHAR (32)
    		);
    		TRUNCATE TABLE companyTempTabl_temp;
    		
    		#数据库表uapcompany关联临时表companyTempTabl_Qurey查询,并将查询结果插入 临时表companyTempTabl_temp
    		INSERT INTO companyTempTabl_temp (id, `name`, attr, parentId) SELECT
    			uapcompany.id,
    			uapcompany.`name`,
    			uapcompany.attr,
    			uapcompany.parentId
    		FROM
    			uapcompany,
    			companyTempTabl_Qurey
    		WHERE
    			uapcompany.parentId = companyTempTabl_Qurey.id;
    		
    		#删除临时表companyTempTabl_Qurey数据
    		DELETE FROM companyTempTabl_Qurey;
    		
    		#将临时表companyTempTabl_temp的数据 插入companyTempTabl_Qurey临时表,用作下一个循环的条件
    		INSERT INTO companyTempTabl_Qurey (id, `name`, attr, parentId) SELECT
    			companyTempTabl_temp.id,
    			companyTempTabl_temp.`name`,
    			companyTempTabl_temp.attr,
    			companyTempTabl_temp.parentId
    		FROM
    			companyTempTabl_temp;
    		
    		#将临时表companyTempTabl_temp的数据 插入到companyTempTabl_Result临时表(该表的数据也是我们最终要返回的数据)
    		INSERT INTO companyTempTabl_Result (id, `name`, attr, parentId) SELECT
    			companyTempTabl_temp.id,
    			companyTempTabl_temp.`name`,
    			companyTempTabl_temp.attr,
    			companyTempTabl_temp.parentId
    		FROM
    			companyTempTabl_temp;
    		
    		#删除companyTempTabl_temp数据
    		DROP TABLE companyTempTabl_temp;
    		
    		#数据库表uapcompany关联 临时表companyTempTabl_Qurey查询统计,并将结果赋值给变量flag
    		SELECT
    			count(1) INTO flag
    		FROM
    			uapcompany,
    			companyTempTabl_Qurey
    		WHERE
    			uapcompany.parentId = companyTempTabl_Qurey.id;
    	END WHILE;
    	SELECT id ,`name`,attr,parentId  FROM companyTempTabl_Result;
    
    END

     然后保存

    测试一下,点击运行

    输入参数,点击确定,结果如下图所示

    我们在dao层只需要调用一次该 存储过程,就可以返回自己想要的数据,存储过程中创建的临时表随着链接的释放自动删除

  • 相关阅读:
    Laravel自定义分页样式
    mysql中 key 、primary key 、unique key 和 index 有什么不同
    PHP RSA公私钥的理解和示例说明
    PHP操作Excel – PHPExcel 基本用法
    Yii 1.1 常规框架部署和配置
    阿里云服务器 Ubuntu 安装 LNMP
    全国地区sql表
    十道海量数据处理面试题与十个方法大总结
    Hibernate中对象的三种状态以及Session类中saveOrUpdate方法与merge方法的区别
    乐观锁与悲观锁——解决并发问题
  • 原文地址:https://www.cnblogs.com/hjw-zq/p/8820810.html
Copyright © 2011-2022 走看看