精华内容
下载资源
问答
  • 动态SQL 和静态SQL区别

    千次阅读 2018-08-20 11:24:57
    所谓SQL的静态和动态,是指SQL语句在何时...静态SQL 动态SQL SQL语句直接嵌入到宿主编程语言,程序需要预编译处理这些嵌入的SQL语句 SQL语句一般作为宿主语言的变量出现。嵌入式动态SQL应用需要预编译,非嵌...

           所谓SQL的静态和动态,是指SQL语句在何时被编译和执行,二者都是用在SQL嵌入式编程中的,这里所说的嵌入式是指将SQL语句嵌入在高级语言中,而不是针对于单片机的那种嵌入式编程。

    二者区别 :

    静态SQL动态SQL
    SQL语句直接嵌入到宿主编程语言,程序需要预编译处理这些嵌入的SQL语句SQL语句一般作为宿主语言的变量出现。嵌入式动态SQL应用需要预编译,非嵌入式SQL应用则无需预编译
    SQL语句在程序被编译时已知,涉及的数据库对象已存在SQL语句在程序被编译时未知,涉及的数据库对象可以是运行时才创建的
    SQL语句在程序运行前被编译SQL语句在程序运行时被编译
    SQL语句的编译结果在DB2的目录(catalog)中持久化保存SQL语句的编译结果缓存在数据库的内存里
    运行时读取目录(catalog)运行时编译SQL语句需要对目录(catalog)加锁
    SQL语句的优化是根据编译时的数据库统计信息进行的,不能完全反映运行时的情况SQL语句的优化是根据运行时的数据库统计信息进行的
    对SQL语句所访问的数据对象的权限检查是在绑定时进行的对SQL语句所访问的数据对象的权限检查是在运行时进行的
    权限控制的粒度是包(package,一组SQL语句的编译结果),用户仅需要访问包的权限权限控制的粒度是SQL语句,用户需要具有访问SQL语句中每个数据对象的权限
    如果SQL语句中的对象被绑定,如DDL执行,整个包都需要重新绑定当SQL语句中的对象被修改时,仅执行过的语句在下次运行时需要重新编译

    静态SQL 

           在某种高级语言中,如果嵌入了SQL语句,而这个SQL语句的主体结构已经明确,例如在Java的一段代码中有一个待执行的SQL“select * from t1 where c1>5”,在Java编译阶段,就可以将这段SQL交给数据库管理系统去分析,数据库软件可以对这段SQL进行语法解析,生成数据库方面的可执行代码,这样的SQL称为静态SQL,即在编译阶段就可以确定数据库要做什么事情。


    动态SQL

           而如果嵌入的SQL没有明确给出,如在Java中定义了一个字符串类型的变量sql:String sql;,然后采用preparedStatement对象的execute方法去执行这个sql,该sql的值可能等于从文本框中读取的一个SQL或者从键盘输入的SQL,但具体是什么,在编译时无法确定,只有等到程序运行起来,在执行的过程中才能确定,这种SQL叫做动态SQL。例如每一种数据库软件都有能够执行SQL语句的界面,那个界面接收的SQL就是动态SQL,因为数据库厂商在做这个界面时,并不知道用户会输入哪些SQL,只有在该界面执行后,接收了用户的实际输入,才知道SQL是什么。


           另外还要注意一点,在SQL中如果某些参数没有确定,如"select * from t1 where c1>? and c2<?",这种语句是静态SQL,不是动态SQL,虽然个别参数的值不知道,但整个SQL的结构已经确定,数据库是可以将它编译的,在执行阶段只需将个别参数的值补充进来即可。

    参考:动态SQL与静态SQL的区别   、    静态SQL和动态SQL 

    展开全文
  • 动态SQL和静态SQL

    2014-03-06 09:37:00
    动态SQL和静态SQL语句 转载于:https://www.cnblogs.com/orchid-sky/p/3583835.html

    动态SQL和静态SQL语句

    转载于:https://www.cnblogs.com/orchid-sky/p/3583835.html

    展开全文
  • Oracle动态SQL和静态SQL比较1.静态SQLSQL与动态SQL Oracle编译PL/SQL程序块分为两个种:其一为前期联编(early binding),即SQL语句在程序编译期间就已经确定,大多数的编译情况属于这种类型;另外一种是后期联编...

    Oracle动态SQL和静态SQL比较

    1.静态SQLSQL与动态SQL
      Oracle编译PL/SQL程序块分为两个种:其一为前期联编(early binding),即SQL语句在程序编译期间就已经确定,大多数的编译情况属于这种类型;另外一种是后期联编(late binding),即SQL语句只有在运行阶段才能建立,例如当查询条件为用户输入时,那么Oracle的SQL引擎就无法在编译期对该程序语句进行确定,只能在用户输入一定的查询条件后才能提交给SQL引擎进行处理。通常,静态SQL采用前一种编译方式,而动态SQL采用后一种编译方式。

    2动态SQL程序开发
      理解了动态SQL编译的原理,也就掌握了其基本的开发思想。动态SQL既然是一种”不确定”的SQL,那其执行就有其相应的特点。Oracle中提供了Execute immediate语句来执行动态SQL,语法如下:

    Excute immediate 动态SQL语句 using 绑定参数列表 returning into 输出参数列表;

    对这一语句作如下说明:
      1)动态SQL是指DDL和不确定的DML(即带参数的DML)
      2)绑定参数列表为输入参数列表,即其类型为in类型,在运行时刻与动态SQL语句中的参数(实际上占位符,可以理解为函数里面的形式参数)进行绑定。
      3)输出参数列表为动态SQL语句执行后返回的参数列表。
      4)由于动态SQL是在运行时刻进行确定的,所以相对于静态而言,其更多的会损失一些系统性能来换取其灵活性。

     为了更好的说明其开发的过程,下面列举一个实例:
      设数据库的他表,其数据为如下:

    ID

    NAME

    SAL

    10

    scott

    3000

    20

    tom

    5000

    30

    jerry

    4500

    要求:
      1.创建该表并输入相应的数据。
      2.根据特定ID可以查询到其姓名和薪水的信息。
      3.根据大于特定的薪水的查询相应的员工信息。
      根据前面的要求,可以分别创建三个过程(均使用动态SQL)来实现:

    过程一:(创建表并插入数据)

    18:16:27 SCOTT@ prod>create or replace procedure p1 as
    18:16:36   2  flag number; 
    18:16:36   3  begin
    18:16:36   4  select count(*) into flag from all_tables where table_name='T1';
    18:16:36   5  if (flag=0) then 
    18:16:36   6  execute immediate 'create table t1(id number,name varchar2(10),sal number)';
    18:16:36   7  else
    18:16:36   8  insert into t1 values (10,'scott',3000);
    18:16:36   9  insert into t1 values (20,'tom',5000);
    18:16:37  10  insert into t1 values (30,'jerry',4500);
    18:16:37  11  end if;
    18:16:37  12  end p1;
    18:16:38  13  /
    Procedure created.
    Elapsed: 00:00:00.20
    18:16:40 SCOTT@ prod>exec p1;
    PL/SQL procedure successfully completed.
    Elapsed: 00:00:00.18
    18:16:47 SCOTT@ prod>select * from t1;
            ID NAME              SAL
    ---------- ---------- ----------
            10 scott            3000
            20 tom              5000
            30 jerry            4500
    Elapsed: 00:00:00.01
    18:16:52 SCOTT@ prod>


    过程二:(按id查询用户信息)

    18:40:24 SCOTT@ prod>create or replace procedure p2 (p_id number) as
    18:40:26   2   v_name varchar2(10);
    18:40:26   3   v_sal number;
    18:40:26   4   begin
    18:40:26   5   execute immediate 'select name,sal  from t1  where id=:1' into v_name,v_sal using p_id;
    18:40:26   6   dbms_output.put_line(v_name ||' Salary is: '||to_char(v_sal));
    18:40:26   7    exception
    18:40:26   8   when others then
    18:40:26   9   dbms_output.put_line('No Data Found');
    18:40:26  10   end p2;
    18:40:26  11   /
    Procedure created.
    Elapsed: 00:00:00.07
    18:40:27 SCOTT@ prod>exec p2(10);
    scott Salary is: 3000
    PL/SQL procedure successfully completed.
    Elapsed: 00:00:00.01
    18:40:32 SCOTT@ prod>exec p2(20);
    tom Salary is: 5000
    PL/SQL procedure successfully completed.
    Elapsed: 00:00:00.02
    18:40:40 SCOTT@ prod>exec p2(30);
    jerry Salary is: 4500
    PL/SQL procedure successfully completed.
    Elapsed: 00:00:00.02
    18:40:45 SCOTT@ prod>


    过程三:(查询薪水大于某个值的员工)

    18:48:59 SCOTT@ prod>create or replace procedure p3(p_sal number) as
    18:50:55   2  r_t1 t1%rowtype;
    18:50:55   3  type c_type is ref cursor;
    18:50:56   4  c1 c_type;
    18:50:56   5  begin
    18:50:56   6  open c1 for '
    18:50:56   7  select * from t1
    18:50:56   8  where sal >:1'
    18:50:56   9  using p_sal;
    18:50:56  10  loop
    18:50:56  11  fetch c1 into r_t1;
    18:50:56  12  exit when c1%notfound;
    18:50:56  13  dbms_output.put_line('Salary higher '||to_char(p_sal)||' Name is:');
    18:50:56  14  dbms_output.put_line('ID is ' ||to_char(r_t1.id)||' Name is: '||r_t1.name);
    18:50:56  15  end loop;
    18:50:56  16  close c1;
    18:50:56  17  end p3;
    18:50:57  18  /
    Procedure created.
    Elapsed: 00:00:00.12
    18:50:58 SCOTT@ prod>exec p3(2000);
    Salary higher 2000 Name is:
    ID is 10 Name is: scott
    Salary higher 2000 Name is:
    ID is 20 Name is: tom
    Salary higher 2000 Name is:
    ID is 30 Name is: jerry
    PL/SQL procedure successfully completed.
    Elapsed: 00:00:00.02
    18:51:15 SCOTT@ prod>


    注意:在过程二中的动态SQL语句使用了占位符“:1“,其实它相当于函数的形式参数,使用”:“作为前缀,然后使用using语句将p_id在运行时刻将:1给替换掉,这里p_id相当于函数里的实参。另外过程三中打开的游标为动态游标,它也属于动态SQL的范畴,其整个编译和开发的过程与execute immediate执行的过程很类似。




     




    本文出自 “天涯客的blog” 博客,请务必保留此出处http://tiany.blog.51cto.com/513694/1422210

    展开全文
  • 动态sql 和静态sql 上篇

    千次阅读 2012-04-11 14:18:32
    1.静态SQL动态SQL: Oracle编译PL/SQL程序块分为两个种: 其一为前期联编(early binding),即SQL语句在程序编译期间就已经确定,大多数的编译情况属于这种类型; 另外一种是后期联编(late ...

    本文讲解基于Oracle高性能动态SQL程序开发。

    1.静态SQL与动态SQL:

    Oracle编译PL/SQL程序块分为两个种:

    其一为前期联编(early binding),即SQL语句在程序编译期间就已经确定,大多数的编译情况属于这种类型;

    另外一种是后期联编(late binding),即SQL语句只有在运行阶段才能建立,例如当查询条件为用户输入时,那么Oracle的SQL引擎就无法在编译期对该程序语句进行确定,只能在用户输入一定的查询条件后才能提交给SQL引擎进行处理。

    通常,静态SQL采用前一种编译方式,而动态SQL采用后一种编译方式。


    本文主要就动态SQL的开发进行讨论,并在最后给出一些实际开发的技巧。

    2. 动态SQL程序开发:

    理解了动态SQL编译的原理,也就掌握了其基本的开发思想。动态SQL既然是一种”不确定”的SQL,那其执行就有其相应的特点。Oracle中提供了Execute immediate语句来执行动态SQL,语法如下:

    Excute immediate 动态SQL语句 using 绑定参数列表 returning into 输出参数列表;

    对这一语句作如下说明:

    1) 动态SQL是指DDL和不确定的DML(即带参数的DML)。

    2) 绑定参数列表为输入参数列表,即其类型为in类型,在运行时刻与动态SQL语句中的参数(实际上占位符,可以理解为函数里面的形式参数)进行绑定。

    3) 输出参数列表为动态SQL语句执行后返回的参数列表。

    4) 由于动态SQL是在运行时刻进行确定的,所以相对于静态而言,其更多的会损失一些系统性能来换取其灵活性。

    为了更好的说明其开发的过程,下面列举一个实例:

    数据库的emp表,其数据为如下:

    ID NAME SALARY
    
    
    100 Jacky 5600
    101 Rose 3000 
    102 John 4500

    要求:

    1.创建该表并输入相应的数据。

    2.根据特定ID可以查询到其姓名和薪水的信息。

    3.根据大于特定的薪水的查询相应的员工信息。

    根据前面的要求,可以分别创建三个过程(均使用动态SQL)来实现:

    过程一:

    create or replace procedure create_table
      as
      begin
         execute immediate 'create table emp (id number,name varchar2(10) salary number; )';   --动态SQL为DDL语句
         insert into empvalues (100,'jacky',5600); 
         insert into empvalues (101,'rose',3000); 
         insert into empvalues (102,'john',4500);
       end create_table;

    过程二:

    create or replace procedure find_info(p_id number) 
         as
            v_name varchar2(10);
           v_salary number;
           begin
              execute immediate 'select name,salary from empwhere id=:1' using p_idreturning into v_name,v_salary; --动态SQL为查询语句
              dbms_output.put_line (v_name ||'的收入为:'||to_char(v_salary));
                exception  when others then  
                          dbms_output.put_line('找不到相应数据');
        end find_info;

    过程三:

    create or replace procedure find_emp(p_salary number) 
      as
          r_emp emp%rowtype;
          type c_type is ref cursor;
          c1 c_type; 
           begin
                open c1 for 'select * from empwhere salary >:1' using p_salary;
                  loop  fetch c1 into r_emp;
                  exit when c1%notfound;
                   dbms_output.put_line ('薪水大于‘||to_char(p_salary)||’的员工为:‘); 
                  dbms_output.put_line('ID为'to_char(r_emp)||' 其姓名为:'||r_emp.name);end loop;
                   close c1;
                  end create_table;

    注意:在过程二中的动态SQL语句使用了占位符“:1“,其实它相当于函数的形式参数,使用”:“作为前缀,然后使用using语句将p_id在运行时刻将:1给替换掉,这里p_id相当于函数里的实参。另外过程三中打开的游标为动态游标,它也属于动态SQL的范畴,其整个编译和开发的过程与 execute immediate执行的过程很类似,这里就不在赘述了。


    3. 动态SQL语句开发技巧

    前面分析到了,动态SQL的执行是以损失系统性能来换取其灵活性的,所以对它进行一定程度的优化也是必要的,笔者根据实际开发经验给出一些开发的技巧,需要指出的是,这里很多经验不仅局限于动态SQL,有些也适用于静态SQL,在描述中会给予标注。

    技巧一:尽量使用类似的SQL语句,这样Oracle本身通过SGA中的共享池来直接对该SQL语句进行缓存,那么在下一次执行类似语句时就直接调用缓存中已解析过的语句,以此来提高执行效率。

    技巧二:当涉及到集合单元的时候,尽量使用批联编。比如需要对id为100和101的员工的薪水加薪10%,一般情况下应该为如下形式:

       declare  
                      type num_list is varray(20) of number;   
                         v_id num_list :=num_list(100,101);   
                 begin   ...   for i in v_id.first .. v_id.last loop   ...  
                     execute immediate 'update emp  
                           set =salary*1.2  where id=:1 '  using v_id(i);   
                         end loop;  
                end;

      

    对于上面的处理,当数据量大的时候就会显得比较慢,那么如果采用批联编的话,则整个集合首先一次性的传入到SQL引擎中进行处理,这样比单独处理效率要高的多,进行批联编处理的代码如下:

         declare   
                           type num_list is varray(20) of number;   
                           v_id num_list :=num_list(100,101);   
                    begin   ...   forall i in v_id.first .. v_id.last loop   ...  
                         execute immediate 'update emp   
                                set =salary*1.2   where id=:1 '   using v_id(i);  
                          end loop;  
                end;

      

    这里是使用forall来进行批联编,这里将批联编处理的情形作一个小结:

    1) 如果一个循环内执行了insert,delete,update等语句引用了集合元素,那么可以将其移 动到一个forall语句中。

    2) 如果select into,fetch into 或returning into 子句引用了一个集合,应该使用bulk collect 子句进行合并。

    3) 如有可能,应该使用主机数组来实现在程序和数据库服务器之间传递参数。


    技巧三:使用NOCOPY编译器来提高PL/SQL性能。缺省情况下,out类型和in out类型的参数是由值传递的方式进行的。但是对于大的对象类型或者集合类型的参数传递而言,其希望损耗将是很大的,为了减少损耗,可以采用引用传递的方式,即在进行参数声明的时候引用NOCOPY关键字来说明即可到达这样的效果。比如创建一个过程:

         create or replace procedure test(p_object in nocopy square)   ...   end;

      

    其中square为一个大的对象类型。这样只是传递一个地址,而不是传递整个对象了。显然这样的处理也是提高了效率。


    4. 小结

    本文对动态SQL的编译原理、开发过程以及开发技巧的讨论,通过本文的介绍后,相信读者对动态SQL程序开发有了一个总体的认识,为今后深入的工作打下一个良好的基础。


    5. 新加动态sql:

        通过绑定变量提高运行性能:

                            看下面的一个例子: 

    create or replace procedure del_dep

     (p_department_id   departments.department_id%type;)

      is

     begin

       execute immdiate 'delete  from  departments where department_id = '|| to_char(p_department_id);

     end;   --这是不绑定变量的一个,对于每一个不同的平p_department_id参数,以上过程都会创建一个游标,这就引起了资源的争用,

    降低效率。  

      ok,再看下一个用了绑定变量的:

    create or replace procedure del_dep

     (p_department_id   departments.department_id%type;)

      is

     begin

       execute immdiate 'delete  from  departments where department_id = :1' using p_department_id;

     end;  --这样,不同的p_department_id会重复利用一个游标。



    后面加一点我自己看的程序,跟上文无关哈:

      By using native dynamic SQL, you can write a smaller, more flexible event dispatcher
    as shown in the following example.
    Example 8–5 Event Dispatching with Native Dynamic SQL

    CREATE OR REPLACE PROCEDURE event_dispatcher

    (p_event_num NUMBER, p_handle NUMBER)

    IS

    BEGIN

    EXECUTE IMMEDIATE

    'BEGIN

    EVENT_HANDLER_' || TO_CHAR(p_event_num) || '(:1);

    END;'

    USING p_handle;

    END;

    /

    Example 8–10 Performing Multiple-Row Queries with Dynamic SQL
    CREATE OR REPLACE PROCEDURE list_employees
    (p_loc VARCHAR2, p_job VARCHAR2)
    IS
    TYPE cur_typ IS REF CURSOR;
    -- Define a cursor variable
    v_emp_cursor cur_typ;
    v_query_str VARCHAR2(1000);
    v_emp_name VARCHAR2(20);
    v_emp_num NUMBER;
    BEGIN
    -- Use concatenation to form the SELECT statement
    v_query_str := 'SELECT ename, empno FROM emp_'
    || p_loc
    || ' WHERE job = :g_job_title';
    -- Open a cursor variable for the query
    OPEN v_emp_cursor FOR v_query_str USING p_job;
    -- Loop through each row to find employees who perform the specified job
    LOOP
    -- Fetch the employee name and ID into variables
    FETCH v_emp_cursor INTO v_emp_name, v_emp_num;
    EXIT WHEN v_emp_cursor%NOTFOUND;
    -- Process row here
    END LOOP;
    CLOSE v_emp_cursor;
    END;
    /
    SHOW ERRORS;


    Example 8–9 Performing Single-Row Queries in Native Dynamic SQL
    CREATE OR REPLACE FUNCTION get_num_of_employees
    (p_loc VARCHAR2, p_job VARCHAR2)
    RETURN NUMBER
    IS
    v_query_str VARCHAR2(1000);

    v_num_of_employees NUMBER;
    BEGIN
    -- Use concatenation to form the table name in the SELECT statement
    v_query_str := 'SELECT COUNT(*) FROM emp_'
    || p_loc
    || ' WHERE job = :1';
    -- Execute the query and put the result row in a variable
    EXECUTE IMMEDIATE v_query_str
    INTO v_num_of_employees
    USING p_job;
    RETURN v_num_of_employees;
    END;
    /
    SHOW ERRORS;


    看完上面三个程序,都懂的话,就差不多了。。

    展开全文
  • 动态SQL与静态SQL区别

    千次阅读 2018-06-15 11:03:10
    动态SQL与静态SQL区别首先,所谓SQL的动态和静态,是指SQL语句在何时被编译和执行,二者都是用在SQL嵌入式编程中的,这里所说的嵌入式是指将SQL语句嵌入在高级语言中,而不是针对于单片机的那种嵌入式编程。...
  • MySQL存储过程中使用动态SQL与静态SQL区别.pdf
  • 动态SQL和静态SQL及绑定变量性能对比1、测试样例下面的三个存储过程,分别使用了动态SQL、绑定变量、静态SQL三种编程方式。具体存储过程内容如下:l)动态SQLcreate or replace procedure proc1 as begin  for...
  • 静态 SQL 和动态 SQL 的比较 静态 SQL 动态 SQL SQL 语句直接嵌入到宿主编程语言,程序需要预编译处理这些嵌入的 SQL 语句 SQL 语句嵌入式动态 SQL 应用需要预编译,非嵌入式 SQL 应用则无需预编译 SQL 语句在程序被...
  • 动态SQL与静态SQL

    千次阅读 2012-06-14 22:18:49
    熟悉MS SQLServer的每一个人都应该意识到避免使用动态SQL的代价是较佳的。...本文将对SQL Server是如何处理动态SQL和静态SQL的原理作一介绍,在本部分,主要讨论一些安全问题,在后续部分将讨论使用动态
  • 首先,所谓SQL的动态和静态,是指SQL语句在何时被编译和执行,二者都是用在SQL嵌入式编程中的,这里所说的嵌入式是指将SQL语句嵌入在高级语言中,而不是针对于单片机的那种嵌入式编程。 静态SQL,在编译阶段就可以...
  • 动态sql 和静态sql 下篇

    千次阅读 2012-04-11 14:22:27
    1、批量绑定让oracle 在对一组值进行sql操作时绑定一个变量,这一组数据可以是任何的plsql的聚合类型(联合数组,内嵌表,可变数组),集合元素必须是sql的数据类型,比如char date mumber。有三个句法支持动态批量...
  • 静态SQL和动态SQL的区别和测试实例

    千次阅读 2015-11-09 16:19:21
    由于近期工作比较悠闲,所以就继续学习了数据库SQL的使用,实际工作中接触最多的是SQL编程,那么本博文就主要介绍动态sql和静态sql的使用方法和区别,方便自己以后回忆学习,如果本博文有幸被浏览者看到,如有瑕疵...
  • 1. 动态SQL和静态SQL:在程序运行的时候才能确定执行计划的SQL是动态的;在程序编译的时候就已经可能知道执行计划的是静态的 静态 SQL:静态 SQL 语句一般用于嵌入式 SQL 应用中,在程序运行前,SQL 语句必须是确定...
  • MySQL存储过程中使用动态SQL与静态SQL区别
  • 动态SQL与静态SQL区别

    2012-03-11 11:43:34
    http://blog.csdn.net/robinson_0612/article/details/6118010 http://topic.csdn.net/t/20020125/14/498918.html http://www.cnblogs.com/kerrycode/archive/2010/08/05/1792671.html
  • MySQL-静态SQL 和动态SQL

    千次阅读 2016-10-28 10:37:42
    所谓SQL动态和静态,是指SQL语句在何时被编译和执行,二者都是用在SQL嵌入式编程中的。
  • 静态SQL和动态SQL

    万次阅读 2012-11-05 15:36:17
    标准的 SQL 语言一般包括三类,即 DDL (Data Definition Language, 数据描述语言 ) 、DML (Data Manipulation Language, 数据操纵语言 ) DCL(Data Control Language,数据控制语言 )。通过这些标准
  • 动态SQL,静态SQL

    千次阅读 2005-10-27 16:08:00
    什么情况下适合使用动态SQL1.执行DDL比如alter table , drop table , create table等,只能用动态SQL2。sql中的table / column信息不明的比如,table_name在写procudre时未知sql_text := select * from ||table_name ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 248,548
精华内容 99,419
关键字:

动态sql和静态sql的区别