mysql存储过程PROCEDURE

关键语法

声明语句结束符

DELIMITER $
此处将语句结束符修改为$
默认情况下,存储过程和默认数据库相关联,如果想指定存储过程创建在某个特定的数据库下,那么在过程名前面加数据库名做前缀

声明存储过程:

CREATE PROCEDURE 存储过程名([[IN |OUT |INOUT ] 参数名 数据类形…])

IN 输入参数:表示调用者向过程传入值(传入值可以是字面量或变量)
OUT 输出参数:表示过程向调用者传出值(可以返回多个值)(传出值只能是变量)
INOUT 输入输出参数:既表示调用者向过程传入值,又表示过程向调用者传出值(值只能是变量)

例如:CREATE PROCEDURE demo_in_parameter(IN p_in int)
demo_in_parameter存储过程需要传入一个int类型的参数,参数名称是p_in

删除存储过程:

DROP PROCEDURE 存储过程名

存储过程开始和结束符号:

BEGIN … END

变量定义:

DECLARE a_int int unsigned default 1;
定义一个int类型的变量,名称是a_int
unsigned 表示无符号,就是非负数
默认是为1

变量赋值:

SET a_int= a_int + 1
设置a_int自增

操作实例

CREATE TABLE `user` (
  `id` int(11) NOT NULL,
  `name` varchar(255) COLLATE utf8_bin DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;

在这里插入图片描述

mysql> delimiter $ #修改结束符
mysql> create procedure in_param(in p_in int)
    -> begin
    -> insert into user(id,name) value(p_in,"zhangsan");
    -> end$
标签使用
[begin_label:] BEGIN
  [statement_list]
END [end_label]

例如:

label1: BEGIN
  label2: BEGIN
    label3: BEGIN
      statements; 
    END label3 ;
  END label2;
END label1

在这里插入图片描述

条件语句

在这里插入图片描述
if-then-else 语句语法:

if 条件 then
	完整的执行语句
else
	完整的执行语句
end if;

在这里插入图片描述

mysql> CREATE PROCEDURE proc2(IN parameter int)
    -> begin
    -> declare var int;
    -> set var=parameter+1;
    -> if var=0 then
    -> select * from user where id = 1;
    -> end if;
    -> if parameter=0 then
    -> select * from user where id = 2;
    -> else
    -> select * from user;
    -> end if;
    -> end;
    -> $

case语句语法:

case 参数
when 0 then		#参数等于0执行
	完整的执行语句;
when 1 then	 	#参数等于1执行
	完整的执行语句;
else	
	完整的执行语句;
end case; 	

循环语句语法:
while ···· end while(执行前进行检查)

declare var int;
set var=0;
while var<6 do
	完整的执行语句;
	set var=var+1;
end while; 	

repeat···· end repeat(执行操作后检查结果)

declare var int
set var=0;
repeat  
	完整的执行语句;
	set var=var+1;
until var>=5  	#循环条件  
end repeat;  

loop ·····end loop(循环不需要初始条件,不需要结束条件,leave 语句的意义是离开循环)

declare var int
set var=0;
loop名称:loop  
	完整的执行语句;
	set var=var+1;
if var >=5 then
leave loop名称;  
end if;
end loop;  
使用事务批量插入数据

在这里插入图片描述

mysql> create procedure bachInsert(in args int)
    -> begin
    -> declare i int default 1;
    -> start transaction;
    -> while i <= args do
    -> insert into user(id,name) value(i,concat("zhangsan-",i));
    -> set i= i + 1;
    -> end while;
    -> commit;
    -> end$
### 解决 MySQL 存储过程中 `PROCEDURE already exists` 错误的方案 #### 1. **错误原因分析** - 当尝试创建一个已经存在的存储过程时,MySQL 数据库会抛出 `PROCEDURE already exists` 的错误。这是因为数据库中已有一个同名的过程定义[^1]。 - 此类问题通常发生在开发人员未检查目标存储过程是否存在的情况下直接运行 `CREATE PROCEDURE` 命令。 --- #### 2. **解决方案** ##### (1)**使用 `DROP PROCEDURE IF EXISTS` 删除已有存储过程** - 在重新创建存储过程之前,可以通过删除旧有的存储过程来避免冲突。这种方法适用于需要完全覆盖现有逻辑的情况。 ```sql DROP PROCEDURE IF EXISTS my_procedure_name; DELIMITER $$ CREATE PROCEDURE my_procedure_name() BEGIN -- 存储过程的具体实现逻辑 END$$ DELIMITER ; ``` 此方法的优点在于简单明了,缺点则是每次都需要手动清理环境,可能会意外丢失某些重要配置或数据关联[^2]。 --- ##### (2)**利用条件判断检测存储过程的存在状态** - 如果希望保留原有存储过程而不被轻易替换,则可以在脚本中加入额外的安全机制以确认是否真的有必要更新现有的定义。 ```sql DELIMITER $$ USE `your_database_name`$$ IF NOT EXISTS ( SELECT * FROM information_schema.routines WHERE routine_type='PROCEDURE' AND routine_schema=DATABASE() AND routine_name='my_procedure_name' ) THEN CREATE PROCEDURE my_procedure_name() BEGIN -- 新增功能代码块 END$$ ELSE ALTER PROCEDURE my_procedure_name(); /* 或者执行修改命令 */ END IF; DELIMITER ; ``` 注意:上述语法并非标准 SQL 支持的形式,而是伪代码示意;实际操作需依据具体需求调整为兼容版本的语言结构[^3]。 --- ##### (3)**采用动态SQL构建更灵活的部署方式** 对于复杂的项目维护场景来说,编写一段通用性强又能适应不同阶段变更要求的自动化脚本显得尤为重要。下面给出一种基于动态SQL的方式作为参考: ```sql SET @proc_exists := NULL; SELECT COUNT(*) INTO @proc_exists FROM INFORMATION_SCHEMA.ROUTINES WHERE ROUTINE_NAME = 'my_procedure_name'; SET @create_sql = CASE WHEN @proc_exists IS NULL OR @proc_exists = 0 THEN CONCAT( 'CREATE PROCEDURE my_procedure_name () BEGIN ', '-- Your Procedure Logic Here', '; END;' ) ELSE '' END ; PREPARE stmt FROM @create_sql; EXECUTE stmt; DEALLOCATE PREPARE stmt; ``` 通过这种方式不仅可以有效规避重复命名引发的问题,还能够在一定程度上提升跨平台迁移效率[^4]。 --- ### 总结 针对 `PROCEDURE already exists` 错误提供了三种主要解决思路:一是强制移除后再重建;二是借助系统表查询预先判定再决定动作方向;三是运用程序化手段自动生成适配语句完成任务切换。每种办法都有各自的适用场合,请根据实际情况选取最合适的那一条路径实施改进措施。 ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值