简体   繁体   中英

Oracle Procedure with return value

I have to write Oracle procedure-The stored procedure should take date as input and return an integer as output. The stored procedure text is as follows:

DECLARE
   bbg_yest       NUMBER;    
   bbg_today      NUMBER;    
   drates_yest    NUMBER;    
   drates_today   NUMBER;    
   equity_yest    NUMBER;    
   equity_today   NUMBER;    
   index_yest     NUMBER;    
   index_today    NUMBER;    
   retval         INTEGER;    
   retval1        INTEGER;    
   retval2        INTEGER;    
   retval3        INTEGER;    
   retval4        INTEGER;
BEGIN                                                                --Check 1
   SELECT COUNT (*)
     INTO bbg_yest
     FROM Crd_Own.Bbg_Oiv v
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO bbg_today
     FROM Crd_Own.Bbg_Oiv v
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

     --Check 2

     SELECT COUNT (*)
       INTO drates_yest
       FROM pm_own.deposit_rates
      WHERE     asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy')
            AND currency_code IN (' USD', 'EUR', 'GBP', 'JPY ')
            AND TERM_WEEKS = 0
            AND MARKET = 'L'
   ORDER BY CURRENCY_CODE, TERM_MONTHS;

     SELECT COUNT (*)
       INTO drates_today
       FROM pm_own.deposit_rates
      WHERE     asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy')
            AND currency_code IN (' USD', 'EUR', 'GBP', 'JPY ')
            AND TERM_WEEKS = 0
            AND MARKET = 'L'
   ORDER BY CURRENCY_CODE, TERM_MONTHS;

   --Check 3

   SELECT COUNT (*)
     INTO equity_yest
     FROM pm_own.BDVD_FORECAST_EQUITY
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO equity_today
     FROM pm_own.BDVD_FORECAST_EQUITY
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

   --Check 4

   SELECT COUNT (*)
     INTO index_yest
     FROM pm_own.BDVD_FORECAST_INDEX
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO index_today
     FROM pm_own.BDVD_FORECAST_INDEX
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

   SELECT ( (bbg_today - bbg_yest) * 100) / bbg_yest INTO retval1 FROM DUAL;

   SELECT ( (drates_today - drates_yest) * 100) / drates_yest
     INTO retval2
     FROM DUAL;

   SELECT ( (equity_today - equity_yest) * 100) / equity_yest
     INTO retval3
     FROM DUAL;

   SELECT ( (index_today - index_yest) * 100) / index_yest
     INTO retval4
     FROM DUAL;

   retval := 0;

   IF retval1 < 0 AND ABS (retval1) > 20
   THEN
      retval := 1;
   ELSIF retval2 < 0 AND ABS (retval2) > 20
   THEN
      retval := 2;
   ELSIF retval3 < 0 AND ABS (retval3) > 20
   THEN
      retval := 3;
   ELSIF retval4 < 0 AND ABS (retval4) > 20
   THEN
      retval := 4;
   END IF;

   DBMS_OUTPUT.put_line (retval);
END;

Please help me in writing correct procedure, with proper call to the stored procedure.

A not tested rough code snippet for procedure is as follows

CREATE OR REPLACE PROCEDURE my_proc (p_param IN DATE, o_param OUT NUMBER)
IS
   bbg_yest       NUMBER;
   bbg_today      NUMBER;
   drates_yest    NUMBER;
   drates_today   NUMBER;
   equity_yest    NUMBER;
   equity_today   NUMBER;
   index_yest     NUMBER;
   index_today    NUMBER;
   retval         INTEGER;
   retval1        INTEGER;
   retval2        INTEGER;
   retval3        INTEGER;
   retval4        INTEGER;
BEGIN                                                                
--Check 1
   SELECT COUNT (*)
     INTO bbg_yest
     FROM Crd_Own.Bbg_Oiv v
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO bbg_today
     FROM Crd_Own.Bbg_Oiv v
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

     --Check 2

     SELECT COUNT (*)
       INTO drates_yest
       FROM pm_own.deposit_rates
      WHERE     asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy')
            AND currency_code IN (' USD', 'EUR', 'GBP', 'JPY ')
            AND TERM_WEEKS = 0
            AND MARKET = 'L'
   ORDER BY CURRENCY_CODE, TERM_MONTHS;

     SELECT COUNT (*)
       INTO drates_today
       FROM pm_own.deposit_rates
      WHERE     asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy')
            AND currency_code IN (' USD', 'EUR', 'GBP', 'JPY ')
            AND TERM_WEEKS = 0
            AND MARKET = 'L'
   ORDER BY CURRENCY_CODE, TERM_MONTHS;

   --Check 3

   SELECT COUNT (*)
     INTO equity_yest
     FROM pm_own.BDVD_FORECAST_EQUITY
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO equity_today
     FROM pm_own.BDVD_FORECAST_EQUITY
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

   --Check 4

   SELECT COUNT (*)
     INTO index_yest
     FROM pm_own.BDVD_FORECAST_INDEX
    WHERE asof_date = TO_DATE ('$last_bus_day', 'mm/dd/yyyy');

   SELECT COUNT (*)
     INTO index_today
     FROM pm_own.BDVD_FORECAST_INDEX
    WHERE asof_date = TO_DATE ('$price_date', 'mm/dd/yyyy');

   SELECT ( (bbg_today - bbg_yest) * 100) / bbg_yest INTO retval1 FROM DUAL;

   SELECT ( (drates_today - drates_yest) * 100) / drates_yest
     INTO retval2
     FROM DUAL;

   SELECT ( (equity_today - equity_yest) * 100) / equity_yest
     INTO retval3
     FROM DUAL;

   SELECT ( (index_today - index_yest) * 100) / index_yest
     INTO retval4
     FROM DUAL;

   retval := 0;

   IF retval1 < 0 AND ABS (retval1) > 20
   THEN
      retval := 1;
   ELSIF retval2 < 0 AND ABS (retval2) > 20
   THEN
      retval := 2;
   ELSIF retval3 < 0 AND ABS (retval3) > 20
   THEN
      retval := 3;
   ELSIF retval4 < 0 AND ABS (retval4) > 20
   THEN
      retval := 4;
   END IF;

   o_param := retval;
END;

Create a function instead of a procedure and use DATE input parameters. Drop the order by in de COUNT(*) queries, they have no purpose if you only select count(*) .

CREATE FUNCTION (last_bus_day DATE, price_date DATE)
RETURN INTEGER
IS

BEGIN
   SELECT COUNT (*)
   INTO bbg_yest
   FROM Crd_Own.Bbg_Oiv v
   WHERE asof_date = last_bus_day;

    SELECT COUNT (*)
    INTO bbg_today
    FROM Crd_Own.Bbg_Oiv v
    WHERE asof_date = price_date;

    etc.

    IF retval1 < 0 AND ABS (retval1) > 20
    THEN
      retval := 1;
    ELSIF retval2 < 0 AND ABS (retval2) > 20
    THEN
      retval := 2;
    ELSIF retval3 < 0 AND ABS (retval3) > 20
    THEN
      retval := 3;
    ELSIF retval4 < 0 AND ABS (retval4) > 20
    THEN
      retval := 4;
    END IF;

    RETURN retval;

END;

Alternatively you can create a function

CREATE OR REPLACE FUNCTION my_function (p_param IN DATE) return number
IS
  l_result number;
BEGIN
   ..calculations...
   return l_result;
END;

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM