我有以下代码:
DELIMITER $$
DROP PROCEDURE IF EXISTS dropAll $$
CREATE PROCEDURE dropAll()
BEGIN
DECLARE done INT DEFAULT FALSE;
DECLARE constraint_name VARCHAR(64);
DECLARE table_name CHAR(64);
DECLARE cur1 CURSOR FOR select CONSTRAINT_NAME, TABLE_NAME from information_schema.TABLE_CONSTRAINTS where CONSTRAINT_TYPE='FOREIGN KEY';
DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = TRUE;
OPEN cur1;
read_loop: LOOP
FETCH cur1 INTO constraint_name, table_name;
IF done THEN
LEAVE read_loop;
END IF;
select table_name, constraint_name;
END LOOP;
CLOSE cur1;
END$$
call dropAll()$$
DELIMITER ;
它应该打印表的名称和约束。但我得到的输出看起来像
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
table_name constraint_name
NULL NULL
如果我在information_schema以外的任何数据库上使用相同的代码,我会获得预期的输出。数据库information_schema有什么不同吗?
答案 0 :(得分:2)
您应该在变量名前加上前缀,以区别于列名。
这应该有效:
DELIMITER $$
DROP PROCEDURE IF EXISTS dropAll $$
CREATE PROCEDURE dropAll()
BEGIN
DECLARE v_done INT DEFAULT FALSE;
DECLARE v_constraint_name VARCHAR(64);
DECLARE v_table_name CHAR(64);
DECLARE cur1 CURSOR FOR select CONSTRAINT_NAME, TABLE_NAME from information_schema.TABLE_CONSTRAINTS where CONSTRAINT_TYPE='FOREIGN KEY';
DECLARE CONTINUE HANDLER FOR NOT FOUND SET v_done = TRUE;
OPEN cur1;
read_loop: LOOP
FETCH cur1 INTO v_constraint_name, v_table_name;
IF v_done THEN
LEAVE read_loop;
END IF;
select v_table_name, v_constraint_name;
END LOOP;
CLOSE cur1;
END$$
call dropAll()$$
DELIMITER ;