Oracle
 sql >> Datenbank >  >> RDS >> Oracle

Array oder Liste in Oracle mit cfprocparam

PL/SQL unterstützt seit Oracle 8.0 Arrays. Früher hießen sie PL/SQL-Tabellen, was alle verwirrte, jetzt heißen sie Sammlungen. Erfahren Sie mehr.

Das Problem ist, dass sie als benutzerdefinierte Typen (d. h. Objekte) implementiert sind. Mein Lesen der ColdFusion-Dokumente schlägt vor, dass cfprocparam unterstützt nur die "primitiven" Datentypen (Zahl, Varchar2 usw.). Daher werden UDTs nicht unterstützt.

Ich bin mir nicht sicher, was Sie damit meinen:

Wenn Sie meinen, Sie möchten eine Zeichenfolge mit kommagetrennten Werten übergeben ....

"Fox in socks, Mr Knox, Sam-I-Am, The Lorax"

dann habe ich einen workaround für dich. Oracle bietet keinen integrierten Tokenizer. Aber vor langer Zeit hat John Spencer in den OTN-Foren eine handgerollte Lösung veröffentlicht, die in Oracle 9i funktioniert. Sie finden es hier.

bearbeiten

Nicht verzweifeln. Die OTN-Foren wurden ein paar Mal aktualisiert, seit John das gepostet hat, und die Formatierung scheint den Code irgendwo auf dem Weg beschädigt zu haben. Es gab ein paar Kompilierungsfehler, die es früher nicht gab.

Ich habe Johns Code neu geschrieben, einschließlich einer neuen Funktion. Der Hauptunterschied besteht darin, dass die verschachtelte Tabelle als SQL-Typ und nicht als PL/SQL-Typ deklariert wird.

create or replace type tok_tbl as table of varchar2(225) 
/

create or replace package parser is

    function my_parse(
          p_str_to_search in varchar2
            , p_delimiter in varchar2 default ',')
          return tok_tbl;

    procedure my_parse(
          p_str_to_search in varchar2
          , p_delimiter in varchar2 default ','
          , p_parsed_table out tok_tbl);

end parser;
/

Wie Sie sehen können, ist die Funktion nur ein Wrapper für die Prozedur.

create or replace package body parser is

    procedure my_parse ( p_str_to_search in varchar2
                          , p_delimiter in varchar2 default ','
                          , p_parsed_table out tok_tbl)
    is
        l_token_count binary_integer := 0;
        l_token_tbl tok_tbl := tok_tbl();
        i pls_integer;
        l_start_pos integer := 1;
        l_end_pos integer :=1;   
    begin

        while l_end_pos != 0
        loop
            l_end_pos := instr(p_str_to_search,p_delimiter,l_start_pos);

            if l_end_pos  != 0 then
                l_token_count := l_token_count + 1;
                l_token_tbl.extend();
                l_token_tbl(l_token_count ) :=
                    substr(p_str_to_search,l_start_pos,l_end_pos - l_start_pos);
                l_start_pos := l_end_pos + 1;
            end if;
        end loop;

        l_token_tbl.extend();
        if l_token_count = 0 then /* we haven't parsed anything so */
            l_token_count := 1;
            l_token_tbl(l_token_count) := p_str_to_search;
        else /* we need to get the last token */
            l_token_count := l_token_count + 1;
            l_token_tbl(l_token_count) := substr(p_str_to_search,l_start_pos);
        end if;
        p_parsed_table := l_token_tbl;
    end my_parse;

    function my_parse ( p_str_to_search in varchar2
                            , p_delimiter in varchar2 default ',')
                          return tok_tbl
    is
        rv tok_tbl;
    begin
        my_parse(p_str_to_search, p_delimiter, rv);
        return rv;
    end my_parse;

end parser;
/

Der Vorteil der Deklaration des Typs in SQL besteht darin, dass wir ihn in einer FROM-Klausel wie dieser verwenden können:

SQL> insert into t23
  2  select trim(column_value)
  3  from table(parser.my_parse('Fox in socks, Mr Knox, Sam-I-Am, The Lorax'))
  4  /

4 rows created.

SQL> select * from t23
  2  /

TXT
------------------------------------------------------------------------------
Fox in socks
Mr Knox
Sam-I-Am
The Lorax

SQL>