Вставить во время выполнения с помощью массового обновления, выдавая внутреннюю ошибку? - PullRequest
1 голос
/ 06 мая 2010

Я пытаюсь сделать таблицу времени выполнения с именем динамической и вставлять в нее данные из индекса по таблице с помощью массового обновления, но когда я пытаюсь выполнить ее, эта ошибка приходит:

ОШИБКА в строке 1: ORA-06550: строка 0, столбец 0: PLS-00801: внутренняя ошибка [74301

]

declare

     type index_tbl_type IS table of
        number
     index by binary_integer;
     num_tbl index_tbl_type;
     TYPE ref_cur IS REF CURSOR;
     cur_emp ref_cur;
    begin
         execute immediate 'create table dynamic (v_num number)';--Creating a run time tabl

         FOR i in 1..10000 LOOP
              execute immediate 'insert into dynamic values('||i||')';--run time insert
         END LOOP;
        OPEN cur_emp FOR 'select * from dynamic';--opening ref cursor
            FETCH cur_emp bulk collect into num_tbl;--bulk inserting in index by table
        close  cur_emp;

        FORALL i in num_tbl.FIRST..num_tbl.LAST --Bulk update
             execute immediate 'insert into dynamic values('||num_tbl(i)||')';
    end;

Ответы [ 2 ]

2 голосов
/ 06 мая 2010

Оператор FORALL ожидает оператор SQL - INSERT, UPDATE или DELETE. EXECUTE IMMEDIATE - это оператор PL / SQL, поэтому ваш код создает это исключение.

Вытягивание такого рода трюков не является хорошей идеей в Production. Таблицы должны быть построены с использованием сценариев DDL, а не динамического SQL.

В любом случае, если вы хотите сделать что-то в этом динамическом стиле, вот как это сделать:

Шаг 1: создайте тип SQL, который можно использовать в инструкциях SQL

SQL> create or replace type my_nums as table of number
  2  /

Type created.

SQL>

Шаг 2: моя версия вашей процедуры, которая использует тип таблицы SQL вместо PL / SQL. Я переписал предложение FORALL как динамический оператор INSERT, который использует коллекцию в предложении TABLE ().

SQL> declare
  2
  3        num_tbl my_nums;
  4        TYPE ref_cur IS REF CURSOR;
  5        cur_emp ref_cur;
  6  begin
  7      execute immediate 'create table dynamic (v_num number)';
  8
  9      FOR i in 1..10000 LOOP
 10           execute immediate 'insert into dynamic values('||i||')'
 11      END LOOP;
 12      OPEN cur_emp FOR 'select * from dynamic';
 13      FETCH cur_emp bulk collect into num_tbl;
 14      close  cur_emp;
 15
 16      execute immediate 
 17         'insert into dynamic select * from table(:1)' using num_tbl;
 18  end;
 19  /

PL/SQL procedure successfully completed.

SQL>

Шаг 3: работает

SQL> select count(*) from dynamic
  2  /

  COUNT(*)
----------
     20000

SQL>
0 голосов
/ 09 мая 2010
DECLARE

            TYPE numlist is table of number index by binary_integer;

            var_num numlist;

BEGIN

            for i in 1..1000 loop

                        var_num(i):=i;

            end loop;

            EXECUTE IMMEDIATE 'create table exe_table(col1 number(10))';

            forall i in var_num.first..var_num.last

                        EXECUTE IMMEDIATE 'INSERT INTO exe_table values(:P)' USING var_num(i);

end loop; 

ПОЧЕМУ тогда это работает?

...