これならできると思います:
curid NUMBER; desctab DBMS_SQL.DESC_TAB; colcnt NUMBER; -- total number of columns res NUMBER; V_ASN_COUNT NUMBER; BEGIN OPEN O_CURSOR FOR SELECT column1, -- a bunch of columns column2, ... COUNT(DISTINCT SI.ASN_NO) OVER (PARTITION BY SI.ASN_NO) AS ASN_COUNT FROM AN_ORDER_INFO OI, AN_SHIPMENT_INFO SI WHERE -- a bunch of criteria curid := DBMS_SQL.TO_CURSOR_NUMBER (O_CURSOR); DBMS_SQL.DESCRIBE_COLUMNS(curid, colcnt, desctab); -- "ASN_COUNT" is the last column, i. e. "colcnt" refers to column number of "ASN_COUNT" -- or set colcnt directly, e.g. colcnt := 12; FOR i IN 1..colcnt LOOP IF desctab(i).col_type = 2 THEN DBMS_SQL.DEFINE_COLUMN(curid, i, V_ASN_COUNT); ELSIF desctab(i).col_type = 12 THEN DBMS_SQL.DEFINE_COLUMN(curid, i, datevar); ....... ELSE DBMS_SQL.DEFINE_COLUMN(curid, i, namevar, 25); END IF; END LOOP; -- I do not know if this loop is needed, perhaps you can simply do -- DBMS_SQL.DEFINE_COLUMN(curid, colcnt, V_ASN_COUNT); -- for a single column res := DBMS_SQL.FETCH_ROWS(curid); -- Fetch only the first row, no loop required DBMS_SQL.COLUMN_VALUE(curid, colcnt, V_ASN_COUNT); -- Loop over all column not required, you just like to get the last column IF V_ASN_COUNT > 1 THEN RAISE MULTIPLE_ASNS; END IF; DBMS_SQL.CLOSE_CURSOR(curid);
プレ>詳細については、Oracle ドキュメントを確認してください:DBMS_SQL.TO_CURSOR_NUMBER 関数。
ただし、カーソルのオープン/巻き戻しの問題は残ります!