zoukankan      html  css  js  c++  java
  • 多测师课堂012_mysql之存储过程 高级讲师肖sir

    一、存储过程介绍
     
    什么是存储过程?
    存储过程是实现某个特定功能的sql语句的集合,编译后的存储过程会保存在数据库中,通过存储过程的名称可以反复的调用执行。
     
    存储过程的优点:
    1.存储过程创建后,就可以反复的调用和使用,不需要重新写复杂的sql语句
    2.创建,修改存储过程不会对数据有任何的影响
    3.存储过程可以通过输入参数返回输出值
    4.通过存储过程中加入控制语句,可以加强sql语句的功能和灵活性
    5.对于单个的增删改查语句(insert,delete,update,select)可以直接封装在一个函数体当中(或者说封装在一个集合当中),存储过程一旦创建可以直接调用,且可以重复的去调用
    6. 单个的SQL语句每次执行都需要数据库进行编译,而存储过程被创建只需要编译一次,后续即可调用。
    7.创建的存储过程,可以重复进行调用,可以减少数据库开发人员的工作量
    8.防止SQL注入 f(x)=x+y
    9、造数据(重点)
     
    在MySQL5.0版本之后就支持存储过程
    存储过程是由sql语句和控制语句组成的
    -------------------------------------------------------------------------------------
    二、基本格式:
    delimiter // 分隔符/定格符
    create procedure 存储过程名( in/out/inout)参数
    begin ---开始
    sql语句 ; ---执行的语句
    end ---结束
    //
     
    call 存储过程名称() 调用一个存储过程
     
    如:
    -- create procedure E() 创建一个存储 ,并命名
    -- begin
    -- select * from dept ;
    -- select * from emp ;
    -- end
    -- //
    call E
     -------------------------------------------------------------------------------------------------------------------
    三、存储过程的基本语句:
    删除一个存储过程
    drop procedure +存储过程名称
     
    查看单个存储过程的详情
    show create procedure +存储过程名称
    查看所有已经创建好的存储过程详情
    show procedure status
    如:show procedure status ;
     
    查询数据库里创建了哪些存储过程
    格式:
    show procedure status where db=“数据库名称”
    show PROCEDURE STATUS where db='dcs02'
     
     -----------------------------------------------------------------------------------------------------------------------------
    四、
    无参数的存储过程
     
    delimiter //
    create procedure 存储名称 ()
    begin
    sql语句 中使用参数
    end
    //
     
    call 存储名称(参数)
    举例:

    delimiter //

    create procedure hz1( )
    BEGIN
    select * from emp ;
    select * from dept;
    END
    //
    call hz1()

     
    ------------------------------------------------------------------------------------------------------------------------------
     in  输入参数
     
    创建一个in有输入参数的存储过程

    #in 表示输入参数
    delimiter //
    create procedure hz2( in x int )
    BEGIN
    select * from emp where dept2=x;
    select * from dept where dept1=x;
    END
    //
    call hz2(101)

    in 输入参数
    in n int     输入参数n,n的数据类型是int
    ---------------------------------------------------------------------------------------------------------
    out 输出参数
     创建一个out ,有输入参数的存储过程
    举例1:
    delimiter //
    create procedure pro_5( out n int)
    select sid into n from emp where name="张三";
    end
    //
    call pro_5( @n)
    select @n
    注意:调用时没有任何输出,只能把调用的结果赋值给传参的参数,调用显示存储过程的值。
     
    ----------------------------------------------------------------------------------------------------------------
    in   和out  结合使用
     案例1:
    delimiter //
    drop procedure if exists pro1;
    create procedure pro1(in n int,out age int)
    BEGIN
    select emp_age into age from emp where emp_id=n;
    end
    //
    call pro1(2,@age)
    select @age
     
    案例2:

    delimiter //
    create procedure hz5( in x int ,out y int )
    BEGIN
    select class into y from student2 where english=x;
    END
    //
    call hz5(56,@y)
    select @y

    ------------------------------------------------------------------------- 
    inout  参数
    案例1:
    delimiter //
    create procedure pro_6( inout n int)
    begin
    set n:=n+1;
    end
    //
    set @n=2
    call pro_6(@n)
    select @n
     
    如果输出的是字符:(out,name char(20))
    注意点:必须要加字符长度,不加字符长度就只会显示name的第一个字符  ,
    ---------------------------------------------------------------------------------------------
     
    三、用户变量: 定义语法:
    set @变量名 ; 赋值语法:
    (1)方式一:普通赋值
    set @变量名:=值;或set @变量名=值;
    select @变量名:=值;
    (2)方式二:通过查询结果为变量赋值
    select 字段|表达式 into  变量名  from 表名 【where 条件】
     ---------------------------------------------------------------------------------------------------
    情况
    场景一:存储内固定插入数据案例讲解:
     
    通过存储过程在一个指定的空表中插入10条数据
     delimiter //

    drop procedure if exists pro4;
    drop table if exists money;
    create procedure pro4()
    BEGIN
    declare i int default 0;# 变量名称i int 数据类型 默认为0
    create table money(id int primary key auto_increment,
    money int(10)
    );
    while(i<10)DO
    insert into money(money) values(100);
    set i=i+1;
    end while;
    select * from money;
    end
    //
    call pro4()

    场景二:存储灵活插入数据案例讲解:(需要插入多少条数据,就插入多少条)

    delimiter //
    drop table if exists money;
    drop procedure if exists pro4;
    create procedure pro4(in x int)
    begin
    declare i int default 0;# 变量名称i int 数据类型 默认为0
    drop table if exists money;
    create table money(id int primary key auto_increment,money int(10));
    while(i<x)DO
    insert into money(money) values(100);
    set i=i+1;
    end while;
    select * from money;
    end
    //

    call pro4(20)

     面试题:

    1、你会存储吗?存储的结构?怎么实现?

    2、存储在工作中用来干嘛?  造数据

    注意点:
    增强
    drop procedure if exists   存储名;  #增强语句的健壮性,判断并删除存在的存储
    drop table if exists  表名;   #增强语句的健壮性,判断并删除存在的表
     declare i int default 0;   declare  声明变量      变量名称i int 数据类型 默认为0
    注意:declare  声明变量后面可以接sql语句,也可以默认值,也可以设置值
     
    方式1:declare    i int default (select   count (id)  from   emp )
    方式2:declare i int default 0;
     
     
    两张表的字段一致,插入数据:
    方法一:insert into 目标表 select * from 来源表;#插入全部数据
    方法二:insert into 目标表(字段 )select 字段1,字段2 from 来源表。
    -------------------------------------------------------------------------------------------------
    2、循环语句
    三种格式:
    WHILE……DO……END WHILE
     
    REPEAT……UNTIL END REPEAT
    LOOP……END LOOP
     
     
     我们这里主讲:
    while 循环语句的结构:
    格式

    while    条件DO
             执行语句
    end while;

    案例:

    while(i<10)DO
    insert into money(money) values(100);
    set i=i+1;
    end while;

     
     ------------------------------------------------------------------------------------------------
     if判断语句
     
    if 条件 THEN
           执行sql1
    else
         执行sql2
    end if;
     
    if单分支案例:
    场景一:

    delimiter //
    drop table if exists money;
    drop procedure if exists pro5;
    create procedure pro5(in a int)
    begin
    if a >10 THEN
    select * from dept ;
    else
    select * from emp ;
    END if;
    end
    //
    call pro5(12)

    --------------------------------------------------------------------------------
    if 多分支
     
    在if判断语句中,有几个判断分支 if ,就有几个结束语 end if
     
    if 条件1 THEN
    执行select * from student limit 0,2;
      else if 条件2 THEN
    执行select * from student limit 0,4;
      else if 条件3 THEN
    执行select * from student limit 0,6;
    else
     select * from student;
    end if;
    end if;
    end if;
     
    案例:场景一
    create procedure pr_add ( in a int)
    begin
    if a >10 THEN
    select * from dept ;
    else if a>0 and a<10 then
    select * from emp ;
    else if a=10 then
    select * from dept,emp where dept1=dept2 ;
    else
    select count(name) from emp ;
    end if;
    end if; 
    end if; 
    end
    //
    
    call pr_add(-1)
    -----------------------------------------------------------------------------------
    练习题:
     
    drop table if exists student;
    create table student2(
    id int primary key ,
    name char(20),
    sex char(10),
    age int(3),
    mobile char(20),
    class char(10),
    english int(10),
    chinese int(10),
    math int(10)
    )engine=INNODB default charset=utf8;
     
    insert into student2 values
    (1,'小红','女',23,'13813828824','1719',77,88,98),
    (2,'小明','男',23,'13713713711','1720',56,66,55),
    (3,'小李','男',23,'15915913911','1719',78,64,87),
    (4,'小张','男',23,'15915913912','1720',77,76,77),
    (5,'小白','女',24,'15915913913','1719',90,89,98),
    (6,'小陈','女',19,'15915913914','1719',84,100,81),
    (7,'小钱','女',20,'15915913915',null,45,99,93);
    面试题:根据student学生表去写
    1.当传入的参数(大于0)小于等于表里面数据的条数时,则根据分组显示班级的总成绩
    2.当传入的参数大于表里面数据的条数时,则统计表里面的数据有多少条
    3.当传入其他,则查询表里面的所有数据 
    select * from student;
    delimiter //
    drop procedure if exists dcs06;
    create procedure dcs06(in n int)
    begin
    declare i int default (select count(1) from student);
    if n>0 && n<=i then #&& 且
    select class,sum(chinese+math+english) from student group by class;
    else if n>i then
    select count(1) from student;
    else
    select * from student;
    end if;
    end if;
    end;
    //
    call dcs02(4)
     
     
    传入数据大于表中已存在的数据的实际记录和行数,则往最高id上自动叠加一行
    方法一:

    delimiter //
    drop procedure if exists bb;
    create procedure bb(in n int)
    begin
    declare i int default (select MAX(id) from student2);
    if n=0 then
    select max(id) from student2;
    else if n>0 && n<=i then
    select * from student2 order by id desc ;
    else
    insert into student2(id) values(i+1);
    select * from student2;
    end if;
    end if;
    end
    //
    call bb(1117)

     
    delimiter // #定义标识符为双斜杠
    drop procedure if exists test; #如果存在test存储过程则删除
    create procedure test() #创建无参存储过程,名称为test
    begin
    declare i int; #申明变量
    set i = 0; #变量赋值
    while i < 10 do #结束循环的条件: 当i大于10时跳出while循环
    insert into test values (i); #往test表添加数据
    set i = i + 1; #循环一次,i加一
    end while; #结束while循环
    select * from test; #查看test表数据
    end
    // #结束定义语句
    call test( ); #调用存储过程
     
    注意事项:
     
    1.分隔符//必须接在 delimiter 后面,不能换行.
    2.存储过程名称后面必须接()   例子:pro_1()
    3.sql    end  if 语句必须用;结尾.
    4.未调用前 sql 语句未使用.调用后才生效.
    5.加强存储过程的功能(表或存储功能都要加分号)
    6.判断存储过程是否存在,存在就删除,不存在就不操作. if  exists
     
  • 相关阅读:
    JZOJ Contest2633 总结
    6813. 【2020.10.05提高组模拟】送信
    HDU 1506 最大子矩形
    2020.10.07【NOIP提高A组】模拟 总结
    6815. 【2020.10.06提高组模拟】树的重心
    2020.10.06【NOIP提高A组】模拟 总结
    2020.10.05【NOIP提高A组】模拟 总结
    gmoj 3976. 【NOI2015模拟1.17】⑨
    2020.09.26【省选组】模拟 总结
    2020.09.19【省选组】模拟 总结
  • 原文地址:https://www.cnblogs.com/xiaolehua/p/14011606.html
Copyright © 2011-2022 走看看