В Oracle, каково различие между открытым - для и открытием курсора с параметрами?

Каково различие между этими двумя частями кода?

TYPE t_my_cursor IS REF CURSOR; 
v_my_cursor t_my_cursor;
OPEN v_my_cursor FOR SELECT  SomeTableID 
        FROM MYSCHEMA.SOMETABLE
        WHERE SomeTableField = p_parameter;

И...

CURSOR v_my_cur(p_parameter VARCHAR2) IS
SELECT SomeTableID
FROM MYSCHEMA.SOMETABLE
WHERE SomeTableField = p_parameter;

OPEN presf_cur(p_subscriber_id);

Они оба, кажется, работают. Действительно ли они - то же или есть ли некоторое различие, о котором я должен знать?

7
задан APC 23 February 2010 в 03:32
поделиться

2 ответа

Второй пример - это явный курсор, и он статичен. То есть, это переменная, связанная с одним оператором SQL. Существует неявный эквивалент...

FOR lrec in ( SELECT  SomeTableID 
              FROM MYSCHEMA.SOMETABLE
              WHERE SomeTableField = p_parameter )
LOOP
    do_something_with (lrec.sometableid);
END LOOP;

Первый пример - это рефлексивный курсор, который является указателем на SQL-запрос и поэтому может быть динамическим. Например, мы можем расширить этот пример следующим образом:

TYPE t_my_cursor IS REF CURSOR; 
v_my_cursor t_my_cursor;

...

if flag = 1 then
    OPEN v_my_cursor FOR SELECT  SomeTableID 
        FROM MYSCHEMA.SOMETABLE
        WHERE SomeTableField = p_parameter;
else
    OPEN v_my_cursor FOR SELECT  SomeTableID 
        FROM MYSCHEMA.ANOTHERTABLE
        WHERE AnotherTableField = p_parameter;
end if;

Или даже:

    l_stmt := 'SELECT * FROM your_table WHERE ';
    if p_parameter is not null then
        l_stmt := l_stmt ||'id = :1'; 
        open v_my_cursor for l_stmt using p_parameter;
    else
        l_stmt := l_stmt ||'created_date > trunc(sysdate)'; 
        open v_my_cursor for l_stmt;
    end if;

Таким образом, использование ref-курсора дает нам гораздо больше контроля над конечным SQL-оператором, который будет выполнен. Другое отличие заключается в том, что, поскольку ref-курсор является указателем, его можно передавать между программами. Это очень полезно для передачи данных из PL/SQL в другие языки, например, в набор результатов JDBC.

6
ответ дан 6 December 2019 в 23:04
поделиться
  1. Строго типизированные курсоры можно «описать».
  2. Если вы создаете API (пакет), вы можете разместить определения курсора на уровне спецификации и дать клиентскому программисту лучшее понимание того, что делает ваш API, и возвращает без необходимости знать исходный код .
  3. Инструменты макета / IDE / GUI , вероятно, будут лучше работать с указателем с именем .
  4. Использование известного типизированного курсора дает, возможно, незначительный выигрыш в производительности; но я бы не стал рассчитывать на что-нибудь существенное.
5
ответ дан 6 December 2019 в 23:04
поделиться
Другие вопросы по тегам:

Похожие вопросы: