开始
1、建立一张学生表
DROP TABLE IF EXISTS `student`;
CREATE TABLE `student` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(256) DEFAULT NULL,
`class` varchar(256) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8;
-- ----------------------------
-- Records of student
-- ----------------------------
INSERT INTO `student` VALUES ('1', '张三', '1班');
INSERT INTO `student` VALUES ('2', '李四', '2班');
INSERT INTO `student` VALUES ('3', '王五', '3班');
INSERT INTO `student` VALUES ('4', '麻子', '1班');
INSERT INTO `student` VALUES ('5', '老王', '3班');
2、建立存储过程
DROP PROCEDURE IF EXISTS forFor;
DELIMITER $$
CREATE PROCEDURE forFor(OUT classNames VARCHAR(1024))
BEGIN
-- 班级名、姓名
DECLARE classs , namess VARCHAR(500);
-- 班级数量、该班级下面学生的数量、班级变量++、学生变量++
DECLARE classNumber , nameNumber, classCount , nameCount INT DEFAULT 0;
-- 建立两个游标,第一个游标用来存储班级、第二个用来存储学生姓名
DECLARE class_csr CURSOR FOR SELECT class FROM student GROUP BY class;
DECLARE name_csr CURSOR FOR SELECT NAME FROM student WHERE class = classs ;
-- 获取按班级分组之后的数量
SELECT COUNT(*) INTO classNumber FROM (SELECT COUNT(*) FROM student GROUP BY class) t;
SET classNames = '' ;
-- 打开班级游标
OPEN class_csr;
-- 开始班级游标循环
class_loop: LOOP
FETCH class_csr INTO classs ;
SET classCount = classCount +1 ;
IF(classCount != 1 ) THEN
SELECT CONCAT(classNames,',' , classs, '(') INTO classNames;
ELSE
SELECT CONCAT(classNames, classs, '(') INTO classNames;
END IF;
-- 获取该班级下面学生的数量
SELECT COUNT(*) INTO nameNumber FROM student WHERE class = classs;
-- 打开学生游标
OPEN name_csr;
-- 开始学生游标循环
name_loop: LOOP
FETCH name_csr INTO namess;
SET nameCount = nameCount +1 ;
IF(nameCount != 1 ) THEN
SELECT CONCAT(classNames,',' , namess) INTO classNames;
ELSE
SELECT CONCAT(classNames , namess) INTO classNames;
END IF;
-- 如果学生变量等于学生数量,那么就终止该游标(第一个)
IF(nameCount = nameNumber) THEN
LEAVE name_loop;
END IF;
-- 结束学生游标循环
END LOOP name_loop;
-- 关闭学生游标
CLOSE name_csr;
SET nameCount = 0 ;
SELECT CONCAT(classNames , ')') INTO classNames;
-- 如果班级变量等于班级数量,那么就终止该游标(第二个)
IF(classCount = classNumber) THEN
LEAVE class_loop;
END IF;
-- 结束班级游标循环
END LOOP class_loop;
-- 关闭班级游标
CLOSE class_csr;
END ;
3、调用存储过程
CALL forFor(@classNames);
SELECT @classNames;
执行结果为:
1班(张三,麻子),2班(李四),3班(王五,老王)