2013-07-31 6 views
2

У меня есть функция, которая объединяет значение для курсора. Теперь он объединяет только 4 столбца и имя столбца должно быть жестко запрограммировано. Есть ли способ получить общее решение для этого, так что, если я пройду курсор, он будет автоматически контактировать данные независимо от имени столбца и количества столбцов в 11g.Конкатенация динамической строки в курсоре

FUNCTION generateData(p_dataCursor IN SYS_REFCURSOR) 
RETURN VARCHAR2 AS 
-- --------------------------------------------------------------------- 
crlf   VARCHAR2(2) := chr(13)||chr(10); 
lv_message  VARCHAR2(32000); 
BEGIN 
    FOR rec IN p_dataCursor 
    LOOP 
     lv_message := lv_message || rec.a||','||rec.b||','||rec.c||','||rec.d || crlf; 
    END LOOP; 
RETURN lv_message; 
END; 

ответ

1

С 11g Oracle встроенного пакетом DBMS_SQL обеспечивает функцию TO_CURSOR_NUMBER - «Эта функция принимает сильно Раскрыта или слабо типизированный исй курсор и преобразует его в число курсора DBMS_SQL.»

Пример кода:

DECLARE 
l_cursor SYS_REFCURSOR; 
FUNCTION generateData(p_dataCursor IN SYS_REFCURSOR) 
RETURN VARCHAR2 AS 
    curs SYS_REFCURSOR := p_dataCursor; 
    l_cursorid NUMBER; 
    l_column_count INTEGER; 
    l_describe_table DBMS_SQL.DESC_TAB; 
    l_numvar NUMBER; 
    l_ignore INTEGER; 
    l_value VARCHAR2(2000); 
    l_coma VARCHAR2(10); 
    crlf   VARCHAR2(2) := chr(13)||chr(10); 
    lv_message  VARCHAR2(32000); 
BEGIN 

    l_cursorid := dbms_sql.to_cursor_number(curs); 

    dbms_sql.describe_columns(l_cursorid, l_column_count, l_describe_table); 

    FOR i IN 1..l_column_count LOOP 
    dbms_sql.define_column(l_cursorid, i, l_value, 2000); 
    END LOOP; 

    LOOP 
    IF DBMS_SQL.FETCH_ROWS(l_cursorid)>0 THEN 
     l_coma := ''; 
     FOR i IN 1..l_column_count LOOP 
     dbms_sql.column_value(l_cursorid, i, l_value); 
     lv_message := lv_message || l_coma || l_value; 
     l_coma := ','; 
     END LOOP; 
     lv_message := lv_message || crlf; 
    ELSE 
     EXIT; 
    END IF; 
    END LOOP; 
    dbms_sql.close_cursor(l_cursorid); 
    RETURN lv_message; 
END; 
BEGIN 
    open l_cursor FOR 'SELECT 1 as A, 2 AS B, 3 AS C, 4 AS D FROM DUAL UNION ALL SELECT 1 as A, 2 AS B, 3 AS C, 4 AS D FROM DUAL'; 
    dbms_Output.put_Line(generateData(l_cursor)); 
END; 
/
Смежные вопросы