MySQL存储过程使用嵌套游标

MySQL存储过程使用嵌套游标

存储过程简介

存储过程是事先经过编译并存储在数据库中的一段 SQL 语句的集合,调用存储过程可以简化应用开发

人员的很多工作,减少数据在数据库和应用服务器之间的传输,对于提高数据处理的效率是有好处的。

存储过程思想上很简单,就是数据库 SQL 语言层面的代码封装与重用。

特点

1.封装,复用 -----------------------> 可以把某一业务SQL封装在存储过程中,需要用到

的时候直接调用即可。

2.可以接收参数,也可以返回数据 --------> 再存储过程中,可以传递参数,也可以接收返回

值。

3.减少网络交互,效率提升 -------------> 如果涉及到多条SQL,每执行一次都是一次网络传

输。 而如果封装在存储过程中,我们只需要网络交互一次可能就可以了。

游标简介

游标(CURSOR)是用来存储查询结果集的数据类型 , 在存储过程和函数中可以使用游标对结果集进

行循环的处理

需求

使用存储过程将博客分类表与博客表数据迁移到category与blog表

博客分类表

sql 复制代码
CREATE TABLE `m_category` (
  `id` bigint(32) NOT NULL AUTO_INCREMENT COMMENT '主键ID',
  `parent_id` bigint(32) unsigned DEFAULT NULL COMMENT '父级分类的ID',
  `name` varchar(512) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '标题',
  `content` text COLLATE utf8mb4_unicode_ci COMMENT '内容描述',
  `summary` text COLLATE utf8mb4_unicode_ci COMMENT '摘要',
  `icon` varchar(128) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '图标',
  `order_num` int(11) DEFAULT NULL COMMENT '排序编码',
  `status` int(2) DEFAULT NULL COMMENT '状态',
  `create_by` bigint(32) DEFAULT NULL COMMENT '创建人',
  `create_time` datetime DEFAULT NULL COMMENT '创建日期',
  `update_by` bigint(32) DEFAULT NULL COMMENT '修改人',
  `update_time` datetime DEFAULT NULL COMMENT '修改时间',
  PRIMARY KEY (`id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci ROW_FORMAT=DYNAMIC COMMENT='分类栏目';

INSERT INTO `m_category`(`id`, `parent_id`, `name`, `content`, `summary`, `icon`, `order_num`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (1, NULL, '提问', NULL, NULL, NULL, NULL, 0, NULL, '2020-04-28 22:36:48', NULL, NULL);
INSERT INTO `m_category`(`id`, `parent_id`, `name`, `content`, `summary`, `icon`, `order_num`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (2, NULL, '分享', NULL, NULL, NULL, NULL, 0, NULL, '2020-04-28 22:36:48', NULL, NULL);
INSERT INTO `m_category`(`id`, `parent_id`, `name`, `content`, `summary`, `icon`, `order_num`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (3, NULL, '讨论', NULL, NULL, NULL, NULL, 0, NULL, '2020-04-28 22:36:48', NULL, NULL);
INSERT INTO `m_category`(`id`, `parent_id`, `name`, `content`, `summary`, `icon`, `order_num`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (4, NULL, '建议', NULL, NULL, NULL, NULL, 0, NULL, '2020-04-28 22:36:48', NULL, NULL);

博客表

sql 复制代码
CREATE TABLE `m_blog` (
  `id` bigint(32) NOT NULL AUTO_INCREMENT COMMENT '主键ID',
  `category_id` bigint(32) DEFAULT NULL COMMENT '分类栏目ID',
  `title` varchar(128) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '标题',
  `content` longtext COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '内容',
  `vote_up` int(11) unsigned NOT NULL DEFAULT '0' COMMENT '支持人数',
  `vote_down` int(11) unsigned NOT NULL DEFAULT '0' COMMENT '反对人数',
  `view_count` int(11) unsigned NOT NULL DEFAULT '0' COMMENT '访问量',
  `status` int(2) DEFAULT NULL COMMENT '状态',
  `create_by` bigint(32) DEFAULT NULL COMMENT '创建人',
  `create_time` datetime DEFAULT NULL COMMENT '创建日期',
  `update_by` bigint(32) DEFAULT NULL COMMENT '修改人',
  `update_time` datetime DEFAULT NULL COMMENT '修改时间',
  PRIMARY KEY (`id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci ROW_FORMAT=DYNAMIC COMMENT='博客表';

INSERT INTO `m_blog`(`id`, `category_id`, `title`, `content`, `vote_up`, `vote_down`, `view_count`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (1, 1, '一起学习Vue', '一起学习Vue吧', 0, 0, 5, NULL, NULL, '2020-04-28 14:41:41', NULL, '2020-04-28 14:41:41');
INSERT INTO `m_blog`(`id`, `category_id`, `title`, `content`, `vote_up`, `vote_down`, `view_count`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (2, 2, '一起学习Java', '一起学习Java吧', 0, 0, 3, NULL, NULL, '2020-04-28 14:55:16', NULL, '2020-04-28 14:55:16');
INSERT INTO `m_blog`(`id`, `category_id`, `title`, `content`, `vote_up`, `vote_down`, `view_count`, `status`, `create_by`, `create_time`, `update_by`, `update_time`) VALUES (3, 3, '一起学习Mysql', '一起学习Mysql吧', 0, 0, 1, NULL, NULL, '2020-04-28 14:55:48', NULL, '2020-04-28 14:55:48');

编写存储过程

sql 复制代码
DROP PROCEDURE tsblog;
CREATE PROCEDURE tsblog ( ) 
BEGIN
 -- 定义变量
	DECLARE cid int;
	DECLARE cname VARCHAR(50);
	DECLARE bcategory_id int;
	DECLARE btitle VARCHAR(50);
	DECLARE bcontent VARCHAR(50);
	DECLARE bcount int DEFAULT 0;
	DECLARE lable INT DEFAULT  0;
	-- 定义外部游标
	DECLARE category_cursor CURSOR FOR select id,name from m_category;
	-- 定义内部游标
	DECLARE blog_cursor CURSOR FOR select category_id,title,content from m_blog;
	-- 当出现NOT FOUND异常时,执行后面的语句
	DECLARE CONTINUE HANDLER FOR NOT FOUND SET lable=1;
	-- 打开游标
	OPEN category_cursor;
	
	-- 创建博客分类表
	DROP table IF EXISTS category;
	create table if not exists category(
		cid int PRIMARY key auto_increment,
		cname VARCHAR(100)
	);
	
	-- 创建博客表
	DROP table IF EXISTS blog;
	create table if not exists blog(
		bid int PRIMARY key auto_increment,
		cid int,
		btitle VARCHAR(50),
		bname VARCHAR(100)
	);
	-- 读取外部游标数据
  category_loop: LOOP
		FETCH category_cursor into cid,cname;
		IF lable=1 THEN
			LEAVE category_loop;
		END IF;
		-- 获取category表插入的ID
		SET bcount := (SELECT AUTO_INCREMENT FROM information_schema.TABLES WHERE TABLE_SCHEMA = 'myblog' AND TABLE_NAME = 'category');
		INSERT into category VALUES(null,cname);
		-- 打开内部游标
		OPEN blog_cursor;
		-- 读取内部游标数据
		blog_loop: LOOP
			FETCH blog_cursor into bcategory_id,btitle,bcontent;
			IF lable=1 THEN
			 LEAVE blog_loop;
			END IF;
			if bcategory_id=cid THEN
			    -- INSERT INTO  blog VALUES (null,(select max(cid) from category),btitle,bcontent);
				INSERT INTO  blog VALUES (null,bcount,btitle,bcontent);
			END IF;
		END LOOP blog_loop;
		-- 关闭内部游标
		CLOSE blog_cursor;
		-- 内部游标执行完,设置为0,继续执行外部游标
		SET lable=0;
  END LOOP category_loop;
	-- 关闭游标
	CLOSE category_cursor;
END;
CALL tsblog ();
相关推荐
陈卓41011 分钟前
MySQL-主从复制&分库分表
android·mysql·adb
IT项目管理44 分钟前
达梦数据库DMHS介绍及安装部署
linux·数据库
你都会上树?1 小时前
MySQL MVCC 详解
数据库·mysql
大春儿的试验田1 小时前
高并发收藏功能设计:Redis异步同步与定时补偿机制详解
java·数据库·redis·学习·缓存
Ein hübscher Kerl.1 小时前
虚拟机上安装 MariaDB 及依赖包
数据库·mariadb
长征coder2 小时前
AWS MySQL 读写分离配置指南
mysql·云计算·aws
醇醛酸醚酮酯2 小时前
Qt项目锻炼——TODO清单(二)
开发语言·数据库·qt
ladymorgana2 小时前
【docker】修改 MySQL 密码后 Navicat 仍能用原密码连接
mysql·adb·docker
PanZonghui2 小时前
Centos项目部署之安装数据库MySQL8
linux·后端·mysql
GreatSQL社区3 小时前
用systemd管理GreatSQL服务详解
数据库·mysql·greatsql