Ihr Typ:
create or replace TYPE INNUMARRAY AS TABLE OF INTEGER;
ist eine Sammlung, die im SQL-Bereich definiert ist.
Ihr übergebenes Argument:
p_strings.CollectionType = OracleCollectionType.PLSQLAssociativeArray;
p_strings.Value = new int[5]{1,2,3,4,5};
ist ein assoziatives Array, das nur in einem PL/SQL-Bereich definiert werden kann (d. h. in einem Paket oder innerhalb eines PL/SQL-Blocks) und nicht in einem SQL-Bereich verwendet werden kann.
Das sind zwei unterschiedliche und inkompatible Datentypen.
Stattdessen können Sie einen assoziativen Array-Typ in einem Paket erstellen und dann jeden Wert manuell aus dem assoziativen Array in eine Sammlung extrahieren, die im SQL-Bereich verwendet werden kann:
CREATE PACKAGE vehicles_pkg IS
TYPE INNUMASSOCARRAY IS TABLE OF INTEGER INDEX BY BINARY_INTEGER;
PROCEDURE v1
(
VehicleGroupID_Array IN INNUMASSOCARRAY
);
END;
/
CREATE PACKAGE BODY vehicles_pkg IS
PROCEDURE v1
(
VehicleGroupID_Array IN INNUMASSOCARRAY
)
IS
p_recordset SYS_REFCURSOR;
p_array INNUMARRAY := INNUMARRAY();
i BINARY_INTEGER;
BEGIN
i := VehicleGroupID_Array.FIRST;
WHILE i IS NOT NULL LOOP
p_array.EXTEND;
p_array( p_array.COUNT ) := VehicleGroupID_Array(i);
i := VehicleGroupID_Array.NEXT(i);
END LOOP;
-- Rest of your procedure using p_array instead of the associative array.
END;
END;
/
kann ich den assoziativen Array-Typ außerhalb des Pakets definieren? Ich möchte, dass sie eigenständig sind.
Nein, aber Sie können ein Paket definieren, das nur den Typ enthält:
CREATE PACKAGE vehicles_pkg IS
TYPE INNUMASSOCARRAY IS TABLE OF INTEGER INDEX BY BINARY_INTEGER;
END;
/
CREATE PROCEDURE v1
(
VehicleGroupID_Array IN vehicles_pkg.INNUMASSOCARRAY
)
IS
p_recordset SYS_REFCURSOR;
p_array INNUMARRAY := INNUMARRAY();
i BINARY_INTEGER;
BEGIN
i := VehicleGroupID_Array.FIRST;
WHILE i IS NOT NULL LOOP
p_array.EXTEND;
p_array( p_array.COUNT ) := VehicleGroupID_Array(i);
i := VehicleGroupID_Array.NEXT(i);
END LOOP;
-- Rest of your procedure using p_array instead of the associative array.
END;
/
Oder erstellen Sie besser einige generisch benannte Typen und eine Funktion im Paket, um sie von einem assoziativen Array in eine Sammlung zu übersetzen, und verwenden Sie sie dann in Ihren Prozeduren wieder:
SQL-Fiddle
Oracle 11g R2-Schema-Setup :
CREATE TYPE IntList AS TABLE OF INTEGER
/
CREATE PACKAGE tools IS
TYPE IntMap IS TABLE OF INTEGER INDEX BY BINARY_INTEGER;
FUNCTION IntMapToList(
i_map IntMap
) RETURN IntList;
END;
/
CREATE PACKAGE BODY tools IS
FUNCTION IntMapToList(
i_map IntMap
) RETURN IntList
IS
o_list IntList := IntList();
i BINARY_INTEGER;
BEGIN
IF i_map IS NOT NULL THEN
i := o_list.FIRST;
WHILE i IS NOT NULL LOOP
o_list.EXTEND;
o_list( o_list.COUNT ) := i_map( i );
i := i_map.NEXT( i );
END LOOP;
END IF;
RETURN o_list;
END;
END;
/
CREATE PROCEDURE v1
(
VehicleGroupID_Array IN tools.IntMap
)
IS
p_recordset SYS_REFCURSOR;
p_array IntList := tools.IntMapToList( VehicleGroupID_Array );
i BINARY_INTEGER;
BEGIN
-- Rest of your procedure using p_array instead of the associative array.
NULL;
END;
/