初學Oracle PL/SQL 【筆記五】

集合:

    PL/SQL 表存在兩種類型:聯合數組(正式說法是索引表)和嵌套表。它們具有相同的結構,並且都使用下標方式來訪問數據行。兩種類型之間的主要差別是:嵌套表可以存儲在數據庫列中,而聯合數組不行。

 

    1.聯合數組

        DECLARE

                TYPE   last_name_type  IS TABLE  OF student.last_name%TYPE

                           INDEX  BY  BINARY_INTEGER;

                   last_name_tab    last_name_type;

              如:

                 DECLARE

                     CURSOR    name_cur   IS   SELECT  last_name   FROM   student  WHERE   rownum <=10;

                     TYPE  last_name_type  IS TABLE OF student.last_name%TYPE

                               INDEX  BY BINARY_INTEGER;

                           last_name_tab    last_name_type;

 

                      v_counter    INTEGER  := 0;

                 BEGIN

                        FOR  name_rec  IN  name_cur  LOOP

                           v_counter := v_counter + 1;

                           last_name_tab(v_counter) := name_rec.last_name;

                           DBMS.OUTPUT.PUT_LINE( ' last_name ( ' || v_counter || ') : '|| last_name_tab(v_counter));

                         END LOOP;

                 END;

 

      2.嵌套表 :首先必須初始化嵌套表,然後才能引用其中的元素。當聲明嵌套表時,嵌套表被自動設置爲NULL。

 

              TYPE  type_name  IS TABLE OF element_type [NOT NULL];

                 table_name   type_name;

          在大多數情況下,無法預知特定嵌套表的值。所以如下語句會產生一個空的,但不是NULL 的嵌套表。

                   last_name_tab := last_name_type();

          如:

              DECLARE

                 CURSOR  name_cur  IS

                     SELECT  last_name  from student  where  rownum <=10;

                  TYPE   last_name_type  IS TABLE  OF student.last_name%TYPE;

                    last_name_tab   last_name_type   :=  last_name_type();

                   v_counter INTEGER :=0;

               BEGIN

                     FOR  name_rec  IN   name_cur  LOOP

                         v_counter  :=  v_counter +1 ;

                         last_name_tab.EXTEND ;

                         last_name_tab(v_counter)  :=  name_rec.last_name;

                         DBMS.OUTPUT.PUT_LINE(' last_name ('|| v_counter || ') : '|| last_name_tab(v_counter));

                    END LOOP;

               END;

 

      集合方法:

如果某特定元素存在於集合中,則EXISTS 會返回TRUE。該方法可以被用於避免SUBSCRIPT_OUTSIDE_LIMIT 異常。

COUNT 返回集合中元素的數量。

EXTEND 會擴展集合的規模。

DELETE 會刪除集合中所有元素,指定範圍的元素,或者特定元素。注意,PL/SQL會保存所刪除元素的佔位符。

FIRST 和 LAST 會返回集合中第一個和最後一個元素的下標。注意,如果嵌套表的第一個元素被刪除,則FIRST 方法會返回大於1 的值。如果從嵌套表個刪除一箇中間元素,則LAST 方法的返回值會大於 COUNT 方法的返回值。

PRIOR  和 NEXT 會返回指定集合下標的前序和後續下標。

TRIM 會從集合的末尾刪除一個,或者指定數量的元素。注意PL/SQL 不會保存被刪除元素的佔位符。

 

如:

 

DECLARE
  TYPE index_by_type  IS TABLE OF NUMBER
  INDEX BY BINARY_INTEGER;
  index_by_table  index_by_type;
 
  type nested_type is table of NUMBER;
  nested_table  nested_type := nested_type(1,2,3,4,5,6,7,8,9,10);
 
BEGIN
  --Populate index by table
  for i in 1..10 loop
    index_by_table(i) := i;
  end loop;
 
  if index_by_table.EXISTS(3)  then
    dbms_output.put_line('index_by_table (3) = ' || index_by_table(3));
  end if;
 
  --delete 10th element form a collection
  nested_table.DELETE(10);
  --delete elements 1 through 3 from a collection
  nested_table.DELETE(1,3);
  index_by_table.DELETE(10);
  DBMS_OUTPUT.PUT_LINE('nested_table.COUNT = '|| nested_table.COUNT);
  DBMS_OUTPUT.PUT_LINE('index_by_table.COUNT = '|| index_by_table.COUNT); 
  DBMS_OUTPUT.PUT_LINE('nested_table.FIRST = '|| nested_table.FIRST);
  DBMS_OUTPUT.PUT_LINE('nested_table.LAST = '|| nested_table.LAST);
  DBMS_OUTPUT.PUT_LINE('index_by_table.FIRST = '|| index_by_table.FIRST);
  DBMS_OUTPUT.PUT_LINE('index_by_table.LAST = '|| index_by_table.LAST);
  DBMS_OUTPUT.PUT_LINE('nested_table.PRIOR(2) = '|| nested_table.PRIOR(2));
  DBMS_OUTPUT.PUT_LINE('nested_table.NEXT(2) = '|| nested_table.NEXT(2));
  DBMS_OUTPUT.PUT_LINE('index_by_table.PRIOR(2) = '|| index_by_table.PRIOR(2));
  DBMS_OUTPUT.PUT_LINE('index_by_table.NEXT(2) = '|| index_by_table.NEXT(2));
 
  --Trim last two elements
  nested_table.TRIM(2);
  --Trim last element
  nested_table.TRIM;
  DBMS_OUTPUT.PUT_LINE('nested_table.LAST = '|| nested_table.LAST); 
end;

 

 

3.變長數組

     語法:

            TYPE  type_name  IS  {VARRAY  |  VARYING  ARRAY } (size_limit)  OF

                   element_type    [NOT  NULL] ;

               varray_name   type_name;

類似於嵌套表,當變長數組被聲明時,自動設置爲NULL。必須在引用單個元素之前,初始化變長數組。

不能對變長數組使用DELETE 方法來刪除其元素。  可使用TRIM方法。

 

DECLARE
  CURSOR name_cur  IS SELECT  last_name from student  where  rownum<=10;
 
  TYPE  last_name_type  IS varray(10)  of student.last_name%TYPE;
  last_name_varray   last_name_type :=last_name_type();
  v_counter  INTEGER  := 0;
 
BEGIN
  FOR  name_rec  in  name_cur  loop
    v_counter  :=  v_counter +1;
    last_name_varray.EXTEND;
    last_name_varray(v_counter) :=  name_rec.last_name  ;
    DBMS_OUTPUT.PUT_LINE('last_name ('|| v_counter || ') : '|| last_name_varray(v_counter));
    END LOOP;
END;

 

declare
  cursor  city_cur is select city from zipcode where rownum <= 10;
  Type city_type  is varray(20)  of zipcode.city%type;
  city_varray  city_type := city_type();
  v_counter  integer :=0;

 

 

begin
  for city_rec in city_cur loop
    v_counter := v_counter +1 ;
    city_varray.extend;
    city_varray(v_counter) := city_rec.city;
  end loop;
  for i in 1..v_counter   loop
    --extend the size of varray by 1 and copy the current element to the last element
    city_varray.extend(1,i); --表示把第i位置上的元素複製一個放在數組後。
    end loop;
  for i in 1..20   loop
    dbms_output.put_line('city_varray ('|| i || ') :'|| city_varray(i));
    end loop;
end; 

 

 

4. 多層集合

declare
  type varray_type1  is varray(4) of integer;
  type varray_type2  is varray(3) of varray_type1;
  varray1  varray_type1  := varray_type1(2,4,6,8);
  varray2  varray_type2  := varray_type2(varray1);
 
begin
  dbms_output.put_line('Varray of integers');
  for i in 1..4 loop
    dbms_output.put_line('varray('|| i || '):' || varray1(i));
    end loop;
 
  varray2.extend;
  varray2(2) := varray_type1(1,3,5,7);
 
  dbms_output.put_line(chr(10) || ' Varray of varrays of integers');
  for i in 1..2 loop
    for j in 1..4 loop
      dbms_output.put_line('varray2('|| i||')(' || j || '): ' || varray2(i)(j));
      end loop;
    end loop;
end;           
   

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章