• Dynamic Cursor in plsql (1)


    DBMS_SQL包提供一个接口,用于执行动态SQL(包括DDL 和DML)。
     DBMS_SQL定义了一个实体叫游标ID,游标ID 是一个PL/SQL整型数,通过游标ID,可以对游标进行操作。
    DBMS_SQL包和本地动态SQL在功能上有许多重叠的地方,但是有的功能只能通过本地动态SQL实现,而有些功能只能通过DBMS_SQL实现。
     
    对于一般的select操作,如果使用动态的sql语句则需要进行以下几个步骤:
    open   cursor---> parse---> define   column---> excute---> fetch   rows---> close   cursor;
    而对于dml操作(insert,update)则需要进行以下几个步骤:
    open   cursor---> parse---> bind   variable---> execute---> close   cursor;
    对于delete操作只需要进行以下几个步骤:
    open   cursor---> parse---> execute---> close   cursor;
    利用DBMS_SQL执行DDL语句:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    CREATE OR REPLACE PROCEDURE CreateTable2 (tablename VARCHAR2)
    IS
    SQL_string VARCHAR2(1000);--存放SQL语句
    V_cur integer;--定义整形变量,用于存放游标
    BEGIN
    SQL_string := 'CREATE TABLE ' || tablename || '(name VARCHAR(20))';
    V_cur := dbms_sql.open_cursor;--打开游标
    dbms_sql.parse(V_cur,SQL_string,DBMS_SQL.NATIVE);--解析并执行SQL语句
    dbms_sql.close_cursor(V_cur);--关闭游标
    END;

     利用DBMS_SQL执行SELECT语句:
    open   cursor---> parse---> define   column---> excute---> fetch   rows---> close   cursor;

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    DECLARE
     v_cursor NUMBER;--游标ID
     sqlstring VARCHAR2(200);--用于存放SQL语句
     v_phone_name  VARCHAR2(20);--手机名字
     v_producer  VARCHAR2(20);--手机生产商
     v_price  NUMBER := 500;--手机价钱
     v_count  INT;--在这里无意义,只是存放函数返回值
    BEGIN
     --:p是占位符
     --SELECT 语句中的第1列是phone_name,第2列是producer ,第3列是price
     sqlstring :='SELECT phone_name,producer,price FROM phone_infor WHERE price > :p';
     v_cursor := dbms_sql.open_cursor;--打开游标;
     dbms_sql.parse(v_cursor ,sqlstring ,dbms_sql.native);--解析动态SQL语句;
      
     --绑定输入参数,v_price的值传给 :p
     dbms_sql.bind_variable(v_cursor ,':p',v_price);
      
     --定义列,v_phone_name对应SELECT 语句中的第1列
     dbms_sql.define_column(v_cursor,1,v_phone_name,20);
     --定义列,v_producer对应SELECT语句中的第2列
     dbms_sql.define_column(v_cursor,2,v_producer,20);
     --定义列,v_price对应SELECT语句中的第3列
     dbms_sql.define_column(v_cursor,3,v_price);
       
     v_count := dbms_sql.EXECUTE(v_cursor); --执行动态SQL语句。
       
     LOOP
      --从游标中把数据检索到缓存区(BUFFER)中,缓冲区 的值只能被函数COULUMN_VALUE()所读取
       EXIT WHEN dbms_sql.fetch_rows(v_cursor)<=0;
      --函数column_value()把缓冲区的列的值读入相应变量中。
      --第1列的值被读入v_phone_name中
       dbms_sql.column_value(v_cursor,1,v_phone_name);
      --第2列的值被读入v_producer中
       dbms_sql.column_value(v_cursor,2,v_producer);
     --第2列的值被读入v_price中
       dbms_sql.column_value(v_cursor,3,v_price);
     --打印变量的值
       dbms_output.put_line(v_phone_name || ' '|| v_producer|| ' '||v_price);
     END LOOP;
     dbms_sql.close_cursor(v_cursor);--关闭游标
     END;

     利用DBMS_SQL执行DML语句:
    open   cursor---> parse---> bind   variable---> execute---> close   cursor;

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    DECLARE
     v_cursor NUMBER;--游标ID
     sqlstring VARCHAR2(200);--用于存放SQL语句
     v_phone_name  VARCHAR2(20);--手机名字
     v_producer  VARCHAR2(20);--手机生产商
     v_price  NUMBER := 500;--手机价钱
     v_count  INT;--被DML语句影响的行数
     BEGIN
      
     sqlstring :='INSERT INTO phone_infor values (:a,:b,:c)';-- :a,:b,:c 是占位符
      
     v_phone_name  := 'S123';
     v_producer  := '索尼AA';
     v_price   := 999;
      
     v_cursor := dbms_sql.open_cursor;--打开游标;
     dbms_sql.parse(v_cursor ,sqlstring ,dbms_sql.native);--解析动态SQL语句;
      
     --绑定输入参数,v_price的值传给 :p
     dbms_sql.bind_variable(v_cursor ,':a',v_phone_name);
     dbms_sql.bind_variable(v_cursor ,':b',v_producer);
     dbms_sql.bind_variable(v_cursor ,':c',v_price);
      
      v_count := dbms_sql.EXECUTE(v_cursor); --执行动态SQL语句。
       
     dbms_sql.close_cursor(v_cursor);--关闭游标
      dbms_output.put_line(' INSERT ' || to_char( v_count) ||' row ');--打印有多少行被插入
      COMMIT;
     END
  • 相关阅读:
    UVA 11354
    HDU 4081 Qin Shi Huang's National Road System 最小/次小生成树的性质
    UVA 10269 Adventure of Super Mario floyd dp
    UVA 11280 Flying to Fredericton 最短路DP
    【专题】树状数组
    【专题】Subsequence
    共享python代码模块
    完全背包
    POJ 3253 Fence Repair
    POJ 3069 Saruman's Army
  • 原文地址:https://www.cnblogs.com/Jeffrey-xu/p/5057685.html
Copyright © 2020-2023  润新知