v_name = Tank War, v _ p ric e = 13.95
v_name = Z F ile s , v _ p ric e = 49.99
v_name = 2412: The Return, v _ p ric e = 14.95
v_name = Space Force 9, v _ p ric e = 13.49
v_name = From Another P la n e t, v _ p ric e = 12.99
v_name = C la s s ic a l Music, v _ p ric e = 10.99
v_name = Pop 3, v _ p ric e = 15.99
v_name = C re a tiv e Y e ll, v _ p ric e = 14.99
v name = My Front Line, v _ p ric e = 13.49
Курсоры и циклы FOR
Для получения доступа к строкам из курсора можно использовать цикл FOR.
При использовании цикла FOR не нужно явно открывать курсор - цикл FOR
сделает это автоматически. В следующем сценарии product_cursor2.sql для
получения доступа к строкам курсора v_product_cursor используется цикл
FOR. Обратите внимание, что этот сценарий содержит меньше строк кода
по сравнению с produc£_cursor.sqclass="underline"
□ --сценарий p ro d u c t_ cu rso r2 .sq l выводит из таблицы products значения
prod u ct_id , name
— и p r ic e , используя для этого курсор
— и цикл FOR
SET SERVEROUTPUT ON
DECLARE
CURSOR v_produ ct_cursor IS
SELECT produ ct_id, name, p r ic e
FROM products
ORDER BY product_id;
BEGIN
FOR v_product IN v_produ ct_cursor LOOP
DBMS_0UTPUT.PUT_LINE(
'p ro d u c t_ id = ' || v _ p ro d u ct.p ro d u c t_ id ||
', name = ' || v_ product.name ||
', p r ic e = ' || v_ p ro d u c t.p r ic e
);
END LOOP;
END;
/
Для выполнения сценария product_cursor2.sql нужно задать команду
типа:
□ SQL> @ «C:\SQL \product_curso r2.sql»
Выходные данные сценария product_cursor2.sql имеют следующий вид:
□ pro du ct_id = 1, name = Modern Science, p r ic e = 19.95
pro du ct_id = 2, name = Chemistry, p r ic e = 30
Знакомство с программированием на PL/SQL 365
product_id = 3, name = Supernova, price = 25.99
product_id = 4, name = Tank War, price = 13.95
product_id = 5, name = Z Files, price = 49.99
product_id = 6, name = 2412: The Return, price = 14.95
product_id = 7, name = Space Force 9, price = 13.49
product_id = 8, name = From Another Planet, price = 12.99
product_id = 9, name = Classical Music, price = 10.99
product_id = 10, name = Pop 3, price = 15.99
product_id = 1 1 , name = Creative Yell, price = 14.99
product_id = 12, name = My Front Line, price = 13.49
Выражение OPEN-FOR
Вы также можете использовать с курсором выражение 0PEN-F0R, которое
добавляет ещё больше гибкости при обработке курсоров, поскольку вы можете
назначить курсор для другого запроса. Это показано в следующем
сценарии product_cursor3.sqclass="underline"
□ — product_cursor3.sql отображает столбцы product_id, name,
и price из таблицы products при помощи переменной курсора
— и выражения 0PEN-F0R -
SET SERVEROUTPUT ON
DECLARE
определим тип REF CURSOR с именем t_product_cursor
TYPE t_product_cursor IS
REF CURSOR RETURN products%ROWTYPE;
определим объект типа t_product_cursor с именем v_product_cursor
v_product_cursor t_product_cursor;
определим объект для хранения столбцов из таблицы products
-- по имени v_product (типа products%ROWTYPE)
v_product рroducts%R0WTYPE;
BEGIN
— назначим запрос для v_product_cursor и откроем его при помощи OPENFOR
OPEN v_product_cursor FOR
SELECT * FROM products WHERE product_id < 5;
используем цикл для получения строк из v_product_cursor в v product
LOOP
FETCH v_product_cursor INTO v_product;
EXIT WHEN v_product_cursor%N0TF0UND;
DBMS_0UTPUT.PUT_LINE(
'product_id = ' || v_product.product_id ||
name = || v_ product.name ||
', price = || v_ product.price
); END LOOP;
366 Глава 11
-- закрываем v_product_cursor
CLOSE v_product_cursor;
END;
В блоке DECLARE следующее выражение объявляет тип REF CURSOR по
имени t_product_cursor (я всегда добавляю t_ в начале имени типа):
□ TYPE t_product_cursor IS
REF CURSOR RETURN products%ROWTYPE;
REF CURSOR представляет собой указатель на курсор и он аналогичен
указателю в языке программирования C++. Предыдущее выражение объявляет
пользовательский тип по имени t_product_cursor, возвращает строку,
содержащую различные столбцы таблицы products (это показано при помощи
%R0WTYPE). Этот пользовательский тип может быть использован при
объявлении реального объекта, как показано в следующем выражении, которое
объявляет объект по имени v_product_cursor:
□ v_product_cursor t_product_cursor;
Следующее выражение объявляет объект для хранения столбцов из
таблицы products по имени v_product (типа products%ROWTYPE):
□ v_product products%ROWTYPE;
В блоке BEGIN курсору v_p roduct_curso г назначается запрос и его открывают
при помощи выражения 0PEN-F0R:
□ OPEN v_product_cursor FOR
SELECT * FROM products WHERE product_id < 5;
После того, как выполнено это выражение, в v_product_cursor будут загружены
первые четыре строки таблицы products. Запрос, назначенный
для v_product_cursor, может быть любым корректным выражением SELECT;
это означает, что вы можете поввторно использовать курсор и назначить
курсору позже в коде PL/SQL другой запрос.
Затемследующийциклпередаётстрокиизу_ргоиис1_сигзог в v_product
и отображает содержимое строки:
□ LOOP
FETCH v_product_cursor INTO v_product;
EXIT WHEN v_product_cursor%NOTFOUND;
DBMS_OUTPUT.PUT_LINE(
‘ product_id = ‘ || v_product.product_id ||
', name = ‘ || v_ product.name ||
price = ‘ || v_ product.price
); END LOOP;
После окончания цикла v_product_cursor закрывается при помощи следующего
выражения: