Query to retrieve previous working day?

I need to write a query that will retrieve the previous working day. Therefore, it must exclude weekends and holidays.
For example, the previous working day for Saturday, February 19 or Sunday, February 20 would be Friday, February 18. And since Monday, February 21 was a holiday for us then the previous working day would also be Friday, February 18.
I've found some queries that allow me to find the previous working day excluding weekends, but I'm having difficulty with the holidays aspect. We have a table called CORPHOLIDAY that contains a field HOLIDAY that stores the holiday dates.
Can I do this with a simple query? I'm not proficient with Oracle, so any and all help is appreciated. Thanks!

Welcome to the forum!
As Dan said, whenever you have a question, it really helps if you post CREATE TABLE and INSERT statements to create whatever tables you need, so people can re-create the problem and test their ideas. Also post the results you want from that data, and your version of Oracle.
The sample data might be as simple as this:
CREATE TABLE     corpholiday
(     holiday     DATE
INSERT INTO corpholiday (holiday) VALUES (DATE '2011-02-21');Here's one way to get the results you want. You enter a starting date (such as February 22, 2011) and the query produces the last working day before that date (in this case, February 18).
WITH     consecutive_days     AS
     SELECT     TO_DATE ( '22-Feb-2011'     -- Input parameter
               , 'DD-Mon-YYYY'
               ) - LEVEL     AS a_date
     FROM     dual
     CONNECT BY     LEVEL     <= 4     -- 1 + Max. possible non-work days
SELECT     MAX (a_date)     AS prev_work_day
FROM           consecutive_days     c
LEFT OUTER JOIN      corpholiday          h  ON     c.a_date     = h.holiday
WHERE     TO_CHAR ( a_date
          , 'Dy'
          , 'NLS_DATE_LANGUAGE=ENGLISH'     -- If necessary
          )     NOT IN ('Sat', 'Sun')
AND     h.holiday     IS NULL
;What you might really like for this job is a WHILE loop, something that would start at the given date, subtract one, test if that day was a work day, and, if necessary, repeat until it did find a work day. That's how you might do it in a procedural language, like PL/SQL, and that's exactly what a lot of people would do: write a PL/SQL function, that could us a WHILE loop. SQL is a non-procedural language, so it doesn't have anything like a loop. Using a CONNECT BY query, as shown above, we can simulate the behavior of a FOR loop, where we do a fixed number of iterations. The query above works by using CONNECT BY to generate the last 4 dates before the given starting date. What is that magic number 4? It's the worst case of how many consecutive days there can be (at least where I work) that is sure to have at least one work day. Where I work, holidays are always at least a week apart, so the longest you can go without a work day is like the example you gave: a Monday (or Friday) holiday, adjacent to the 2 weekend days. You may need to change the number 4 to something higher if, say, December 25 and 26 were both holidays, or if Good Friday and Easter Monday were both holidays.
As posted, the query above works in Oracle 9 (and up), but it can be modified for earlier versions.
Edited by: Frank Kulash on Feb 23, 2011 8:57 PM
Added explanation

Similar Messages

  • How to get the last(latest or previous) working day

    hi,
    using sysdate we may be getting today's date and sysdate-1 will be fetching the yesterday's date. but if sysdate-1 turns to be sunday or a holiday then we need to get the previous date to that holiday date .THe list of holidays are in lt_list_holidays. The Holiday date shall be the holiday_date column. I need a query which displays the last (latest or previous) working day ..
    Please advice
    Edited by: vine on Jul 20, 2010 5:30 AM
    Edited by: vine on Jul 20, 2010 5:51 AM

    Hi,
    vine wrote:
    hi ,
    THe queery seems to be fine but in the middle if we have any holidays and the holidays are in lt_list_holidays table . the name of the holiday date is holiday_date in lt_list_holiday.Is the name of the holiday important? I'll assume not. I'll also assume you have a column d (a DATE) that is the date of the holiday.
    >
    Please adviceThat's quite a different problem from what you first posted.
    Instead of posting a question x, waiting for someone to answer it, and then saying that the problem is really y, don't you think it would be better to post question y in the first place?
    You can do something like this:
    WITH     prev_days     AS
         SELECT     TRUNC (SYSDATE) - LEVEL     AS a_date
         FROM     dual
         CONNECT BY     LEVEL <= 4     -- worst case (see below)
    SELECT     MAX (a_date)     AS previous_work_day
    FROM     prev_days
    WHERE     TO_CHAR (a_date, 'Dy', 'NLS_DATE_LANGUAGE=''ENGLISH''')
                   NOT IN ('Sat', 'Sun')
    AND     NOT EXISTS ( SELECT  1
                   FROM    lt_list_holiday
                   WHERE   d     = prev-days.a_date
    ;Where I work, holidays are never consecutive, in fact, they are always at least 7 days apart, so I can be sure that a period of 4 consectuive days will always contain at least one work day. (There may be two weekend days plus one holiday; that's the worst case.) If you can have two or more holidays in a row, or holidays spaced 3 days apart (so that one might fall on a Friday, and the other on Monday), then increase the "magic number" 4 in
         CONNECT BY     LEVEL <= 4     -- worst caseto something appropriate. If you put it too high (say 10), no serious harm is done.

  • Get Previous Working Day

    Do you know any function module which will give me the previous working day only by ignoring saturdays and sundays and it should NOT consider holidays.
    Example:
    Monday's Date should give me previous friday's date.
    Friday's Date should give me previous thrusday's date

    Hello Ramesh,
    I assume you have your factory calendar ID with you:
    DATA:
        L_V_PREDT        TYPE DATUM, "Next Day.
      L_V_PREDT = SY-DATUM - 1.
    * Get the next Working Day as per Factory Calendar
      CALL FUNCTION 'DATE_CONVERT_TO_FACTORYDATE'
        EXPORTING
          CORRECT_OPTION               = '-' " -VE  to get the previous date
          DATE                         = L_V_PREDT
          FACTORY_CALENDAR_ID          = 'HY' "--> Give your factory cal. ID here
        IMPORTING
          DATE                         = V_PREWD
        EXCEPTIONS
          CALENDAR_BUFFER_NOT_LOADABLE = 1
          CORRECT_OPTION_INVALID       = 2
          DATE_AFTER_RANGE             = 3
          DATE_BEFORE_RANGE            = 4
          DATE_INVALID                 = 5
          FACTORY_CALENDAR_NOT_FOUND   = 6
          OTHERS                       = 7.
      IF SY-SUBRC <> 0.
    *  Do Nothing
      ENDIF.
    If you want to use the FM: BKK_GET_PRIOR_WORKDAY, still then you have to use the operation:
    L_V_PREDT = SY-DATUM - 1.
    And pass L_V_PREDT to the FM. You can test with 23.03.2009 date & check )
    Hope this helps.
    BR,
    Suhas
    Edited by: Suhas Saha on Mar 19, 2009 4:56 PM

  • How to query the number of working days between two dates

    I'm looking for a solution to calculate the number of <i>working</i> days between two dates that I can use in a formated search. 
    Calculating the total number of days is pretty straight forward but does anyone know how to take into account the settings in the HLD1 (Holiday Dates) table?

    Hi Eric,
    If you are purely looking to exclude holidays defined in the HLD1 table, then you should be able to do it with the following query
    NOTE: The following query is an example using OINV table and the fields DOCDATE and DOCDUEDATE for a Particular DOCNUM  'xxx'
    If you planning to use within the SAP module then replace DOCDATE and DOCDUEDATE with dynamic field references $[$x.x.x]
    SELECT DATEDIFF(DAY,T0.DOCDATE,T0.DOCDUEDATE)-
    (SELECT COUNT(STRDATE) FROM HLD1 WHERE STRDATE >= T0.DOCDATE AND STRDATE <= T0.DOCDUEDATE)
    FROM OINV T0
    WHERE T0.DOCNUM = xxx
    Best Wishes
    Suda

  • Calculating Number of Working Days

    Hi All,
    I'm creating a crystal report where I have to calculate the Number of Working Days between a date range, this should exclude the Weekends(done) but also exclude the public holidays which have defined in Holidays Calender.
    I'm not using procedure , Operating directly with tables.
    Any help would be appreciated.
    Regards

    Hello Pari,
    Check Exclude Holidays and weekends from Last7Day function link for function to exclude weekends.
    and How to query the number of working days between two dates to get holidays defined in holiday calander.
    Thanks,
    Neetu

  • Calculate x working days before date

    Dear experts,
    I am trying to find a date that is x working days before another.
    Is that a function module about this?
    Thank you in advance,
    Roxani

    Hi Roxani,
    You can use FM END_TIME_DETERMINE.
    There:
    - Insert in duration the number of days that you want to subtract with the minus sign (ex: -1 for previous working day)
    - Also, insert your factory calendar that you want to be the source of your working days.
    - And, of course, the desired starting date.
    Hope that helps!
    Kind regards,
    Garcia

  • Day is working day

    Hi,
    Is there any FM existing to find today is working day or holiday?
    kaki

    hi kaki,
    just check this ..i got it from SAP help.
    DATA: DATE1        LIKE SCAL-DATE,
          DATE2        LIKE SCAL-DATE,
          CORRECTION   LIKE SCAL-INDICATOR,
          CALENDAR     LIKE SCAL-FCALID,
          FACTORYDATE  LIKE SCAL-FACDATE,
          WORKDAY      LIKE SCAL-INDICATOR.
          CALL FUNCTION 'DATE_CONVERT_TO_FACTORYDATE'
               EXPORTING  DATE                 = DATE1
                           CORRECT_OPTION       = CORRECTION
                           FACTORY_CALENDAR_ID  = CALENDAR
               IMPORTING  DATE                 = DATE2
                           FACTORYDATE          = FACTORYDATE
                           WORKINGDAY_INDICATOR = WORKDAY
               EXCEPTIONS CORRECT_OPTION_INVALID     = 1
                            DATE_AFTER_RANGE           = 2
                           DATE_BEFORE_RANGE          = 3
                           DATE_INVALID               = 4
                           FACTORY_CALENDAR_NOT_FOUND = 5.
    check the workday and analyze...
    the documentation says..
    <b>Flag whether date is a workday
    Possible values are:
    ' ' the specified date is a working day.
    '+' the specified date is not a working day,
        the following working day is returned.
    '-' the specified date is not a working day,
        the previous working day is returned.</b>

  • Previous business day in sql query

    Hi,
    Is there a way to calculate the previous business day on teh sql query without using a function call.
    Typically in the query where clause as seen below:
    eg)
    select * from sales where sale_date ='+previous_buss_day+'
    If so please let me know....Thnx in advanc.

    that depends if your organization has a defined set of business days that will includes non-working days (holidays, etc.). if there is you need to have a lookup table that has a listing of all available normal business day and non-working days. then match it up with your transaction table. otherwise you can use the current system date less 1 days.
    e.g.
    select * from sales where sale_date = trunc(sysdate-1)

  • Query for geetiing no.of working days

    Hi All,
    How can we write a query for geetiing no.of working days in Oracle Apps.
    Basically we need to mention no.of working days in the Work-Flow Form but not the no.of days.
    So how can we write a query for getting no.of working days.and Where can we get the tables?
    Is there any need of calendar in WIP(Work in Process) Module?
    Can any one please help me out.
    Thanks in Advance,
    Dhana

    Hi,
    Please see if these documents help.
    Note: 43276.1 - Calculating the Number of Working Days
    Note: 1018913.102 - How to Find Number of Days - Valid Working Days - Between Two Dates
    Regards,
    Hussein

  • Finding number of working days during query execution

    Hi ,
    We have a requirement to calculate number of working days during query execution. In the cube we got "received date", this will be used as a variable in the query. Based on the received date value entered, query needs to display number of products received from past 1, 2,3,4 days (working days should include weekends or public holidays).
    1day     2 days     3 days     4 days   5 days 
    10         12            20            15          20
    to me it appears as I need to create virtual key figures.
    Regards,
    Ramz

    Hi ramesh,
    First try to create formula variables for start data and end date to calculate the no of working days.
    Create a Variable ZSTDT --of type replacement path.
    Type of Variable = Formula
    Variable Name = ZSTDT
    Characteristic = <info object>
    For Intervals Use = Select From Value
    Offset Start = 0000 Offset Length = 0000
    Replacement var with : key
    use the same steps to create one more formula variable to get end date.
    Now create a formula to get the No of days.
    once after getting no of days you can create buckets as per your need.
    for more info check the below links
    http://www.sd-solutions.com/SAP-HCM-BW-Replacement-Path-Variables.html
    http://www.sdn.sap.com/irj/scn/go/portal/prtroot/docs/library/uuid/30f15839-0cf1-2b10-c6a7-ebe68cc87cdc?quicklink=index&overridelayout=true

  • I previously uploaded images onto my desktop to work on in Lightroom 5.2. I worked on a few of the images days ago and just now getting back to them. My problem is I can only access the images I previously worked on and all the rest it says images not ava

    I previously uploaded images onto my desktop to work on in Lightroom 5.2. I worked on a few of the images days ago and just now getting back to them. My problem is I can only access the images I previously worked on and all the rest it says images not available but all the images are still right on my desktop.

    ... and all the rest it says images not available
    Normally this happens because you moved, renamed or deleted these photos (or the folders that contain them) outside of Lightroom. This is how to fix the problem: Adobe Lightroom - Find moved or missing files and folders

  • Calculation of no. of working days (per Factory Cal) between 2 date chars

    This question could be considered to be in continuation of a previous post called "Working days of month with factory calendar"
    I have two date Characteristics: say Date1 and Date2. I need to find the number of working days between them based on the factory calendar.
    (And yes we have already defined the default factory calendar in IMG under 'General Reporting settings' ).
    The previous post proposed the following:
    1) Convert date1 into factorydate (standard functionmodule)
    2) Convert date2 into factorydate (standard functionmodule)
    Perform date1 - date2 to get number of working days.
    I agree that there is a std function module to convert cal date to factory date called: 'DATE_CONVERT_TO_FACTORYDATE'
    But what are the steps for calling the conversion? Should I create a new Formula variable of 'Customer Exit type' give it a name and define the Function module in CMOD? But then how do I attach the formula variable to the date characteristic. Note that my infoobjects are Chars so I cannot do date1- date2 in the query as is possible with keyfigures!
    Please help! (my version is BW 3.0)
    Thanks
    Naresh

    Hi,
    For the above scenario when you need to calculate date 1 - date 2. we can't build a new formulae or calculated KF directly because those are the chars.
    So we need make chars to act as KF through Formulae with replacement path.
    create a formulae variable on those 2 Date chars with Processing type as replaccement then those 2 Dates can be avilable to build a formulae as ur requirement.
    Let me know if you need any more information.
    Thanks,
    Raju

  • Show Working days transaction on Weekends and Holidays

    Hi,
    I have an objective to show last working days transaction (consider Friday) on Saturday and Sunday, also
    if the next day is also a Holiday then i have to post previous days transactions on Holiday too.
    Example:I need to show Friday Sep 1,2006 Transactions on
    Sep 2,2006
    Sept 3,2006
    Sep 4,2006 (Labor Day -- Holdiay)
    Restriction:PL/SQL not allowed( i know it is hard to believe ..sorry)
    Here is the Query that i have written which takes care of Sat and Sundays.I am having problem with Posting the data on Holidays.
    -- This Query selects all working days only
    select TRADE_DATE,
    Case when PORT_ID = 'FFSEX5' then SUM(PRINCIPAL) End as FFSDirect,
    Case when PORT_ID = 'FFSEX5' then trunc(AVG(RATE),2) End as FFSDirect_Avg,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then SUM(PRINCIPAL) End as FFSBroker,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then trunc(AVG(RATE),2) End as FFSBroker_Avg,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then SUM(PRINCIPAL) End as Euro3,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then trunc(AVG(RATE),2) End as Euro3_Avg,0 AS FLAG
    FROM CV_TRADE_HIST
    Group by port_id,Trade_date
    Union
    -- Accumulates Saturdays
    select (TRADE_DATE+1) as Trade_Date,
    Case when PORT_ID = 'FFSEX5' then SUM(PRINCIPAL) End as FFSDirect,
    Case when PORT_ID = 'FFSEX5' then trunc(AVG(RATE),2) End as FFSDirect_Avg,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then SUM(PRINCIPAL) End as FFSBroker,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then trunc(AVG(RATE),2) End as FFSBroker_Avg,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then SUM(PRINCIPAL) End as Euro3,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then trunc(AVG(RATE),2) End as Euro3_Avg,0 AS FLAG
    FROM CV_TRADE_HIST Where to_char(trade_date,'dy')='fri'
    Group by port_id,Trade_date
    Union
    -- Accumulates Sundays
    select (TRADE_DATE+2) as Trade_Date,
    Case when PORT_ID = 'FFSEX5' then SUM(PRINCIPAL) End as FFSDirect,
    Case when PORT_ID = 'FFSEX5' then trunc(AVG(RATE),2) End as FFSDirect_Avg,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then SUM(PRINCIPAL) End as FFSBroker,
    Case when PORT_ID in ('FFSEX3', 'FFSEX2', 'CLS') then trunc(AVG(RATE),2) End as FFSBroker_Avg,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then SUM(PRINCIPAL) End as Euro3,
    Case when PORT_ID in ('EPIEX3', 'ACK', 'ETCEX3', 'CKD') then trunc(AVG(RATE),2) End as Euro3_Avg,0 AS FLAG
    FROM CV_TRADE_HIST Where to_char(trade_date,'dy')='fri'
    Group by port_id,Trade_date
    UNION
    -- TO ADD HOLIDAYS TO THE RECORD SET
    SELECT HOLI_DT AS TRADE_DATE,
    0 AS FFSDirect,
    0 AS FFSDirect_Avg,
    0 AS FFSBroker,
    0 AS FFSBroker_Avg,
    0 as Euro3,
    0 AS Euro3_Avg,
    0 AS Euro4,
    1 AS FLAG
    FROM V_INTR_SRC_HOLIDAY
    WHERE TO_NUMBER(TO_CHAR(HOLI_DT,'YYYY'))=2006 and TO_CHAR(HOLI_DT,'DY') NOT IN ('SAT','SUN')
    ORDER BY 1 DESC
    Logic i was trying (I NEED TO POST THE PREVIOUS DAYS TRANSACTIONS WHERE FLAG=1 WHICH IS A HOLIDAY.using Lag())
    ****My constraint is no PL/SQL and no DML is allowed.
    Please let me know is there anyway i can achieve this.I tried using Lag(), it did not work for me,Any suggestions?
    Thank you,
    Jay Brahmanapalli
    Message was edited by:
    user530625

    Here's a simple version:
    Setup:
    drop table trade_history
    create table trade_history
    ( trade_date date not null
    , amount number not null
    , ticker varchar2(6) not null
    declare
        tdate date;
        tamount number;
    begin
        tdate := trunc(sysdate);
        for i in 1..365 loop
            tdate := tdate - 1;
            tamount := 200 - i;
            insert into trade_history (trade_date, amount, ticker)
            values (tdate, tamount, 'ORCL');
        end loop;
    end;
    commit
    drop table holidays
    create table holidays
    ( holiday_date date not null
    , previous_business_date date not null
    , holiday_name varchar2(240)
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('25-DEC-05','24-DEC-05','Christmas Day')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('26-DEC-05','24-DEC-05','Boxing Day')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('06-SEP-06','05-SEP-06','A midweek example')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('04-SEP-06','01-SEP-06','A Monday example')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('07-AUG-06','04-AUG-06','A two day post w/e example')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('08-AUG-06','04-AUG-06','A two day post w/e example')
    insert into holidays (holiday_date, previous_business_date, holiday_name)
    values ('26-DEC-06','24-DEC-06','Boxing Day 2006')
    commit
    /And a very simple example query
    select last_business_day, ticker, sum(amount), count(amount)
    from (
    select nvl(hol.previous_business_date, trade_date)
           - case to_char(nvl(hol.previous_business_date, trade_date),'D')
                        when '7' then 2
                        when '6' then 1
                        else 0
                        end last_business_day
         , ticker, amount
    from   trade_history th
    left join holidays hol on hol.holiday_date = th.trade_date
    group by last_weekday, ticker
    order by 1,2You should be able to build on that example, I hope. If you can't add the previous_business_date to your holiday table, then it gets slightly more complicated (because you have to skip back through consecutive holidays AND weekends AND any more consecutive holidays - ie in UK you'd have to skip back through Easter Monday, the Easter Weekend and Good Friday - last busines day is what we call Maundy Thursday.
    HTH
    Regards Nigel

  • Working Day - Is there a table in the DW that stores non-working days?

    Scenario
    I need to query the previous or next working using W_DAY_D to compute certain daily statistics. At the moment I can use W_DAY_D and exclude DAY_NAMES like weekends. However I cannot use it for say Bank Holidays.
    Is there any table in the DW that stores the working days or to put the other way the holidays? Are there any flags on that table that would suggest the day is a working day?

    You will need to extend your W_DAY_D for that and load it according to your "working days" logic (i.e. including bank holidays etc.).
    Each row will need new foreign keys like "PREV_WRK_DAY_WID" and "NXT_WRK_DAY_WID". With those you can then join in new time dim aliases which will yield the results you're looking for. Basically the old Siebel Analytics approach before the integrated time series calculations.
    Cheers,
    C.

  • SQL query to retrieve totals from "supporting Details"

    We've had a strange issue where the totals from the supporting details aren't adding up to the value submitted in essbase.
    In effect our RDMS is out of sync with Planning.
    In order to remedy this, I'm trying to build a SQL query to retrieve the value of the supporting details.
    Here is my Sql statement so far :
    SELECT
    HO1.OBJECT_NAME SCENARIO,
    HO2.OBJECT_NAME ACCOUNT,
    HO3.OBJECT_NAME ENTITY,
    HO4.OBJECT_NAME Month,
    HO5.OBJECT_NAME Version,
    HO6.OBJECT_NAME Currency,
    HO7.OBJECT_NAME Year,
    HO8.OBJECT_NAME Project,
    HO10.OBJECT_NAME CC,
    HO12.OBJECT_NAME Grplcl,
    HO13.OBJECT_NAME Product,
    HO15.OBJECT_NAME SalesRegion,
    HO16.OBJECT_NAME ContractAnalysis,
    HO17.OBJECT_NAME IC,
    SUM(NVL(HCDI.VALUE,0)) AMOUNT
    FROM hsp_column_detail HCD,
    hsp_column_detail_ITEM HCDI,
    HSP_OBJECT HO1,
    HSP_OBJECT HO2,
    HSP_OBJECT HO3,
    HSP_OBJECT HO4,
    HSP_OBJECT HO5,
    HSP_OBJECT HO6,
    HSP_OBJECT HO7,
    HSP_OBJECT HO8,
    HSP_OBJECT HO10,
    HSP_OBJECT HO12,
    HSP_OBJECT HO13,
    HSP_OBJECT HO15,
    HSP_OBJECT HO16,
    HSP_OBJECT HO17
    WHERE hcd.detail_id = hcdi.detail_id
    AND hcd.dim1 = ho1.object_id
    AND hcd.dim2 = ho2.object_id
    AND hcd.dim3 = ho3.object_id
    AND hcd.dim4 = ho4.object_id
    AND hcd.dim5 = ho5.object_id
    AND hcd.dim6 = ho6.object_id
    AND hcd.dim7 = ho7.object_id
    AND hcd.dim8 = ho8.object_id
    AND hcd.dim10 = ho10.object_id
    AND hcd.dim12 = ho12.object_id
    AND hcd.dim13 = ho13.object_id
    AND hcd.dim15 = ho15.object_id
    AND hcd.dim16 = ho16.object_id
    AND hcd.dim17 = ho17.object_id
    and hcdi.generation = 0
    GROUP BY HO1.OBJECT_NAME, HO2.OBJECT_NAME, HO3.OBJECT_NAME, HO4.OBJECT_NAME,
    HO5.OBJECT_NAME,
    HO6.OBJECT_NAME,
    HO7.OBJECT_NAME,
    HO8.OBJECT_NAME,
    HO10.OBJECT_NAME,
    HO12.OBJECT_NAME,
    HO13.OBJECT_NAME,
    HO15.OBJECT_NAME,
    HO16.OBJECT_NAME,
    HO17.OBJECT_NAME
    ORDER BY HO1.OBJECT_NAME, HO3.OBJECT_NAME, HO2.OBJECT_NAME

    This query works using PL SQL and has been used on Oracle 9.2.3.
    Cheers,
    Jeremie
    Here is the Query:
    set serveroutput on;
    set serveroutput on size 1000000;
    --set buffer_size 10000000;
    --set line_size 2000;
    --DBMS_OUTPUT.size = 2000000;
    DECLARE
    CURSOR BUDGET_HEADERS_CU IS
    SELECT
    hcd.detail_id,
    HO1.OBJECT_NAME SCENARIO,
    HO2.OBJECT_NAME ACCOUNT,
    HO3.OBJECT_NAME ENTITY,
    HO4.OBJECT_NAME Month,
    HO5.OBJECT_NAME Version,
    HO6.OBJECT_NAME Currency,
    HO7.OBJECT_NAME Year,
    HO8.OBJECT_NAME Project,
    HO10.OBJECT_NAME CC,
    HO12.OBJECT_NAME Grplcl,
    HO13.OBJECT_NAME Product,
    HO15.OBJECT_NAME SalesRegion,
    HO16.OBJECT_NAME ContractAnalysis,
    HO17.OBJECT_NAME IC,
    hcd.dim1 SCENARIO_id,
    hcd.dim2 ACCOUNT_id,
    hcd.dim3 ENTITY_id,
    hcd.dim4 Month_id,
    hcd.dim5 Version_id,
    hcd.dim6 Currency_ID,
    hcd.dim7 Year_ID,
    hcd.dim8 Project_ID,
    hcd.dim10 CC_ID,
    hcd.dim12 Grplcl_ID,
    hcd.dim13 Product_ID,
    hcd.dim15 SalesRegion_ID,
    hcd.dim16 ContractAnalysis_ID,
    hcd.dim17 IC_ID
    FROM hsp_column_detail HCD, /*hsp_column_detail_item HCDi,*/
    HSP_OBJECT HO1,
    HSP_OBJECT HO2,
    HSP_OBJECT HO3,
    HSP_OBJECT HO4,
    HSP_OBJECT HO5,
    HSP_OBJECT HO6,
    HSP_OBJECT HO7,
    HSP_OBJECT HO8,
    HSP_OBJECT HO10,
    HSP_OBJECT HO12,
    HSP_OBJECT HO13,
    HSP_OBJECT HO15,
    HSP_OBJECT HO16,
    HSP_OBJECT HO17
    WHERE /*hcd.detail_id = hcdi.detail_id
    AND*/ hcd.dim1 = ho1.object_id
    AND hcd.dim2 = ho2.object_id
    AND hcd.dim3 = ho3.object_id
    AND hcd.dim4 = ho4.object_id
    AND hcd.dim5 = ho5.object_id
    AND hcd.dim6 = ho6.object_id
    AND hcd.dim7 = ho7.object_id
    AND hcd.dim8 = ho8.object_id
    AND hcd.dim10 = ho10.object_id
    AND hcd.dim12 = ho12.object_id
    AND hcd.dim13 = ho13.object_id
    AND hcd.dim15 = ho15.object_id
    AND hcd.dim16 = ho16.object_id
    AND hcd.dim17 = ho17.object_id
    and HO5.OBJECT_NAME = 'Working'
    --and hcdi.generation != 0
    --and hcdi.label like 'JRTEST-%'
    --and hcd.detail_id = 253102
    /*GROUP BY HCD.Dim1, HCD.Dim2, HCD.Dim3, HCD.Dim4,
    HCD.Dim5,
    HCD.Dim6,
    HCD.Dim7,
    HCD.Dim8,
    HCD.Dim10,
    HCD.Dim12,
    HCD.Dim13,
    HCD.Dim15,
    HCD.Dim16,
    HCD.Dim17*/;
    CURSOR BUDGET_DETAILS_CU(
    /*scenario_p in varchar2,
    account_p in varchar2,
    entity_p in varchar2,
    month_p in varchar2,
    version_p in varchar2,
    currency_p in varchar2,
    year_p in varchar2,
    project_p in varchar2,
    cc_p in varchar2,
    grplcl_p in varchar2,
    product_p in varchar2,
    salesregion_p in varchar2,
    contractanalysis_p in varchar2,
    ic_p in varchar2*/
    detail_id_p in number
    IS
    SELECT
    /* HO1.OBJECT_NAME SCENARIO,
    HO2.OBJECT_NAME ACCOUNT,
    HO3.OBJECT_NAME ENTITY,
    HO4.OBJECT_NAME Month,
    HO5.OBJECT_NAME Version,
    HO6.OBJECT_NAME Currency,
    HO7.OBJECT_NAME Year,
    HO8.OBJECT_NAME Project,
    HO10.OBJECT_NAME CC,
    HO12.OBJECT_NAME Grplcl,
    HO13.OBJECT_NAME Product,
    HO15.OBJECT_NAME SalesRegion,
    HO16.OBJECT_NAME ContractAnalysis,
    HO17.OBJECT_NAME IC, */
    label,
    NVL(HCDI.VALUE,0) AMOUNT,
    HCDI.Position,
    HCDI.operator,
    HCDI.generation
    FROM /*hsp_column_detail HCD,*/
    hsp_column_detail_ITEM HCDI
    /* HSP_OBJECT HO1,
    HSP_OBJECT HO2,
    HSP_OBJECT HO3,
    HSP_OBJECT HO4,
    HSP_OBJECT HO5,
    HSP_OBJECT HO6,
    HSP_OBJECT HO7,
    HSP_OBJECT HO8,
    HSP_OBJECT HO10,
    HSP_OBJECT HO12,
    HSP_OBJECT HO13,
    HSP_OBJECT HO15,
    HSP_OBJECT HO16,
    HSP_OBJECT HO17*/
    --WHERE hcd.detail_id = hcdi.detail_id
    WHERE hcdi.detail_id = detail_id_p
    /*AND hcd.dim1 = ho1.object_id
    AND hcd.dim2 = ho2.object_id
    AND hcd.dim3 = ho3.object_id
    AND hcd.dim4 = ho4.object_id
    AND hcd.dim5 = ho5.object_id
    AND hcd.dim6 = ho6.object_id
    AND hcd.dim7 = ho7.object_id
    AND hcd.dim8 = ho8.object_id
    AND hcd.dim10 = ho10.object_id
    AND hcd.dim12 = ho12.object_id
    AND hcd.dim13 = ho13.object_id
    AND hcd.dim15 = ho15.object_id
    AND hcd.dim16 = ho16.object_id
    AND hcd.dim17 = ho17.object_id*/
    --and hcdi.generation != 0
    --and label like 'JRTEST-%'
    /*AND HCD.Dim1 = scenario_p
    AND HCD.Dim2 = account_p
    AND HCD.Dim3 = entity_p
    AND HCD.Dim4 = month_p
    AND HCD.Dim5 = version_p
    AND HCD.Dim6 = currency_p
    AND HCD.Dim7 = year_p
    AND HCD.Dim8 = project_p
    AND HCD.Dim10 = cc_p
    AND HCD.Dim12 = grplcl_p
    AND HCD.Dim13 = product_p
    AND HCD.Dim15 = salesregion_p
    AND HCD.Dim16 = contractanalysis_p
    AND HCD.Dim17 = ic_p*/
    ORDER BY hcdi.position;
    -- Variable Declaration
    running_total_ln number :=0;
    prev_running_total_ln number :=0;
    add_amount number :=0;
    multiply_amount number :=1;
    prev_generation number :=0;
    prev_add_amount number :=0;
    prev_multiply_amount number :=1;
    running_total_gen0 number :=0;
    running_gen0_op number :=0;
    running_total_gen1 number :=0;
    running_gen1_op number :=0;
    running_total_gen2 number :=0;
    running_gen2_op number :=0;
    running_total_gen3 number :=0;
    running_gen3_op number :=0;
    running_total_gen4 number :=0;
    running_gen4_op number :=0;
    running_total_gen5 number :=0;
    running_gen5_op number :=0;
    output_file utl_file.file_type;
    -- Begin PL/SQL processing
    BEGIN
    --DBMS_OUTPUT.
    DBMS_OUTPUT.ENABLE(1000000);
    DBMS_OUTPUT.PUT_LINE('Begin Processing');
    output_file := utl_file.fopen ('C:\temp', 'test.txt', 'W');
    -- Begin Header For Loop
    FOR BUDGET_HEADERS_CV IN BUDGET_HEADERS_CU
    LOOP
    --Reset Running Totals
    running_total_ln:=0;
    prev_running_total_ln:=0;
    add_amount:=0;
    multiply_amount:=1;
    prev_generation:=0;
    prev_add_amount:=0;
    prev_multiply_amount:=1;
    running_total_gen0:=0;
    running_gen0_op:=0;
    running_total_gen1:=0;
    running_gen1_op:=0;
    running_total_gen2:=0;
    running_gen2_op:=0;
    running_total_gen3:=0;
    running_gen3_op:=0;
    running_total_gen4:=0;
    running_gen4_op:=0;
    running_total_gen5:=0;
    running_gen5_op:=0;
    -- Begin Detail For Loop
    FOR BUDGET_DETAILS_CV IN BUDGET_DETAILS_CU(
    BUDGET_HEADERS_CV.Detail_ID
    /*BUDGET_HEADERS_CV.SCENARIO_ID,
    BUDGET_HEADERS_CV.ACCOUNT_ID,
    BUDGET_HEADERS_CV.ENTITY_ID,
    BUDGET_HEADERS_CV.Month_ID,
    BUDGET_HEADERS_CV.Version_ID,
    BUDGET_HEADERS_CV.Currency_ID,
    BUDGET_HEADERS_CV.Year_ID,
    BUDGET_HEADERS_CV.Project_ID,
    BUDGET_HEADERS_CV.CC_ID,
    BUDGET_HEADERS_CV.Grplcl_ID,
    BUDGET_HEADERS_CV.Product_ID,
    BUDGET_HEADERS_CV.SalesRegion_ID,
    BUDGET_HEADERS_CV.ContractAnalysis_ID,
    BUDGET_HEADERS_CV.IC_ID*/
    LOOP
    -- Null;
    add_amount :=0;
    multiply_amount :=1;
    IF BUDGET_DETAILS_CV.OPERATOR = 1 THEN
    add_amount := BUDGET_DETAILS_CV.Amount;
    End if;
    IF BUDGET_DETAILS_CV.OPERATOR = 2 THEN
    add_amount := BUDGET_DETAILS_CV.Amount * -1;
    End if;
    IF BUDGET_DETAILS_CV.OPERATOR = 3 THEN
    multiply_amount := BUDGET_DETAILS_CV.Amount;
    End if;
    IF BUDGET_DETAILS_CV.OPERATOR = 4 THEN
    multiply_amount := 1/BUDGET_DETAILS_CV.Amount;
    End if;
    IF BUDGET_DETAILS_CV.Position = 0 then
    running_total_gen0 := add_amount*multiply_amount;-- we are dealing with the first line
    Else
    if BUDGET_DETAILS_CV.GENERATION = prev_generation then
    -- run whatever total we are on up
    if BUDGET_DETAILS_CV.GENERATION = 0 then
    running_total_gen0 := (running_total_gen0 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 1 then
    running_total_gen1 := (running_total_gen1 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 2 then
    running_total_gen2 := (running_total_gen2 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 3 then
    running_total_gen3 := (running_total_gen3 + add_amount)*multiply_amount;
    end if;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = prev_generation +1 then
    -- we are going up a generation
    -- (we cannot go up to gen0
    if BUDGET_DETAILS_CV.GENERATION = 1 then
    running_total_gen1:=0;-- reset gen1 counter
    running_gen0_op:=BUDGET_DETAILS_CV.OPERATOR; -- Store the sign for later operation
    running_total_gen0 := running_total_gen0/prev_multiply_amount - prev_add_amount; -- Remove parent from Gen 0 total
    running_total_gen1 := (running_total_gen1 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 2 then
    running_total_gen2:=0;-- reset gen1 counter
    running_gen1_op:=BUDGET_DETAILS_CV.OPERATOR; -- Store the sign for later operation
    running_total_gen1 := running_total_gen1/prev_multiply_amount - prev_add_amount; -- Remove parent from Gen 1 total
    running_total_gen2 := (running_total_gen2 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 3 then
    running_total_gen3:=0;-- reset gen1 counter
    running_gen2_op:=BUDGET_DETAILS_CV.OPERATOR; -- Store the sign for later operation
    running_total_gen2 := running_total_gen2/prev_multiply_amount - prev_add_amount; -- Remove parent from Gen 2 total
    running_total_gen3 := (running_total_gen3 + add_amount)*multiply_amount;
    end if;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = prev_generation - 1 then
    -- we are Down a generation
    if BUDGET_DETAILS_CV.GENERATION = 0 then
    --we need to "add" back the previous gen 1 parent
    IF running_gen0_op = 1 THEN
    running_total_gen0 := running_total_gen0 + running_total_gen1;
    End if;
    IF running_gen0_op = 2 THEN
    running_total_gen0 := running_total_gen0 - running_total_gen1;
    End if;
    IF running_gen0_op = 3 THEN
    running_total_gen0 := running_total_gen0 * running_total_gen1;
    End if;
    IF running_gen0_op = 4 THEN
    running_total_gen0 := running_total_gen0 / running_total_gen1;
    End if;
    -- we need to add the current member to the gen0
    running_total_gen0 := (running_total_gen0 + add_amount)*multiply_amount;
    END IF;
    if BUDGET_DETAILS_CV.GENERATION = 1 then
    --we need to "add" back the previous gen 2 parent
    IF running_gen1_op = 1 THEN
    running_total_gen1 := running_total_gen1 + running_total_gen2;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen1 := running_total_gen1 - running_total_gen2;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen1 := running_total_gen1 * running_total_gen2;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen1 := running_total_gen1 / running_total_gen2;
    End if;
    -- we need to add the current member to the gen1
    running_total_gen1 := (running_total_gen1 + add_amount)*multiply_amount;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = 2 then
    --we need to "add" back the previous gen 3 parent
    IF running_gen1_op = 1 THEN
    running_total_gen2 := running_total_gen2 + running_total_gen3;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen2 := running_total_gen2 - running_total_gen3;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen2 := running_total_gen2 * running_total_gen3;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen2 := running_total_gen2 / running_total_gen3;
    End if;
    -- we need to add the current member to the gen2
    running_total_gen2 := (running_total_gen2 + add_amount)*multiply_amount;
    end if;
    end if;
    if BUDGET_DETAILS_CV.GENERATION = prev_generation - 2 then
    -- we are Down 2 generations
    if BUDGET_DETAILS_CV.GENERATION = 0 then
    --we need to "add" back the previous gen 2 parent
    IF running_gen1_op = 1 THEN
    running_total_gen1 := running_total_gen1 + running_total_gen2;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen1 := running_total_gen1 - running_total_gen2;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen1 := running_total_gen1 * running_total_gen2;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen1 := running_total_gen1 / running_total_gen2;
    End if;
    --we need to "add" back the previous gen 1 parent
    IF running_gen0_op = 1 THEN
    running_total_gen0 := running_total_gen0 + running_total_gen1;
    End if;
    IF running_gen0_op = 2 THEN
    running_total_gen0 := running_total_gen0 - running_total_gen1;
    End if;
    IF running_gen0_op = 3 THEN
    running_total_gen0 := running_total_gen0 * running_total_gen1;
    End if;
    IF running_gen0_op = 4 THEN
    running_total_gen0 := running_total_gen0 / running_total_gen1;
    End if;
    -- we need to add the current member to the gen0
    running_total_gen0 := (running_total_gen0 + add_amount)*multiply_amount;
    END IF;
    if BUDGET_DETAILS_CV.GENERATION = 1 then
    --we need to "add" back the previous gen 3 parent
    IF running_gen1_op = 1 THEN
    running_total_gen2 := running_total_gen2 + running_total_gen3;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen2 := running_total_gen2 - running_total_gen3;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen2 := running_total_gen2 * running_total_gen3;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen2 := running_total_gen2 / running_total_gen3;
    End if;
    --we need to "add" back the previous gen 2 parent
    IF running_gen1_op = 1 THEN
    running_total_gen1 := running_total_gen1 + running_total_gen2;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen1 := running_total_gen1 - running_total_gen2;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen1 := running_total_gen1 * running_total_gen2;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen1 := running_total_gen1 / running_total_gen2;
    End if;
    -- we need to add the current member to the gen1
    running_total_gen1 := (running_total_gen1 + add_amount)*multiply_amount;
    END IF;
    if BUDGET_DETAILS_CV.GENERATION = prev_generation - 3 then
    -- we are Down 3 generations
    if BUDGET_DETAILS_CV.GENERATION = 0 then
    --we need to "add" back the previous gen 3 parent
    IF running_gen1_op = 1 THEN
    running_total_gen2 := running_total_gen2 + running_total_gen3;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen2 := running_total_gen2 - running_total_gen3;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen2 := running_total_gen2 * running_total_gen3;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen2 := running_total_gen2 / running_total_gen3;
    End if;
    --we need to "add" back the previous gen 2 parent
    IF running_gen1_op = 1 THEN
    running_total_gen1 := running_total_gen1 + running_total_gen2;
    End if;
    IF running_gen1_op = 2 THEN
    running_total_gen1 := running_total_gen1 - running_total_gen2;
    End if;
    IF running_gen1_op = 3 THEN
    running_total_gen1 := running_total_gen1 * running_total_gen2;
    End if;
    IF running_gen1_op = 4 THEN
    running_total_gen1 := running_total_gen1 / running_total_gen2;
    End if;
    --we need to "add" back the previous gen 1 parent
    IF running_gen0_op = 1 THEN
    running_total_gen0 := running_total_gen0 + running_total_gen1;
    End if;
    IF running_gen0_op = 2 THEN
    running_total_gen0 := running_total_gen0 - running_total_gen1;
    End if;
    IF running_gen0_op = 3 THEN
    running_total_gen0 := running_total_gen0 * running_total_gen1;
    End if;
    IF running_gen0_op = 4 THEN
    running_total_gen0 := running_total_gen0 / running_total_gen1;
    End if;
    -- we need to add the current member to the gen0
    running_total_gen0 := (running_total_gen0 + add_amount)*multiply_amount;
    END IF;
    end if;
    END IF;
    End IF;
    END LOOP; -- End of Detail Loop
    --DBMS_OUTPUT.PUT_LINE(BUDGET_HEADERS_CV.SCENARIO||';'||BUDGET_HEADERS_CV.ACCOUNT||';'||BUDGET_HEADERS_CV.ENTITY||';'||BUDGET_HEADERS_CV.Month||';'||BUDGET_HEADERS_CV.Version||';'||BUDGET_HEADERS_CV.Currency||';'||BUDGET_HEADERS_CV.Year||';'||BUDGET_HEADERS_CV.Project||';'||BUDGET_HEADERS_CV.CC||';'||BUDGET_HEADERS_CV.Grplcl||';'||BUDGET_HEADERS_CV.Product||';'||BUDGET_HEADERS_CV.SalesRegion||';'||BUDGET_HEADERS_CV.ContractAnalysis||';'||BUDGET_HEADERS_CV.IC||';'||running_total_gen0);
    utl_file.put_line(output_file,BUDGET_HEADERS_CV.SCENARIO||';'||BUDGET_HEADERS_CV.ACCOUNT||';'||BUDGET_HEADERS_CV.ENTITY||';'||BUDGET_HEADERS_CV.Month||';'||BUDGET_HEADERS_CV.Version||';'||BUDGET_HEADERS_CV.Currency||';'||BUDGET_HEADERS_CV.Year||';'||BUDGET_HEADERS_CV.Project||';'||BUDGET_HEADERS_CV.CC||';'||BUDGET_HEADERS_CV.Grplcl||';'||BUDGET_HEADERS_CV.Product||';'||BUDGET_HEADERS_CV.SalesRegion||';'||BUDGET_HEADERS_CV.ContractAnalysis||';'||BUDGET_HEADERS_CV.IC||';'||running_total_gen0);
    /*BUDGET_HEADERS_CV.SCENARIO, BUDGET_HEADERS_CV.ACCOUNT, BUDGET_HEADERS_CV.ENTITY, BUDGET_HEADERS_CV.Month, BUDGET_HEADERS_CV.Version,BUDGET_HEADERS_CV.Currency, BUDGET_HEADERS_CV.Year, BUDGET_HEADERS_CV.Project, BUDGET_HEADERS_CV.CC, BUDGET_HEADERS_CV.Grplcl, BUDGET_HEADERS_CV.Product, BUDGET_HEADERS_CV.SalesRegion, BUDGET_HEADERS_CV.ContractAnalysis, BUDGET_HEADERS_CV.IC */
    END LOOP; -- End of Header Loop
    --DBMS_OUTPUT.PUT_LINE('Total');
    -- DBMS_OUTPUT.PUT_LINE('End Processing');
    utl_file.fclose(output_file);
    END;
    Edited by: JeremieR on Apr 18, 2011 5:02 AM

Maybe you are looking for

  • Excise invoice issue with AT1

    While i creation of Excise invoice with this t.code J1IIN with refference to Billing document this is autometically generated the Excise invoice and while i save this document the system thowing the following eror. AT1 :  Debit =             77,01  C

  • How can I create a new itunes account?

    I bought an ipod touch for my kid and I linked it to my itunes account.  I changed my mind, How can I change this and make an itunes account for my kid?

  • Zen touch problem

    Hello everyone. I have a 20gig zen touch which was working fine . I have the latest drivers / firmware installed . But when i connect it to the computer windows says found new hardware creative zen , then opens the install new hardware part , even al

  • Is there a limit on in app purchases

    I purchased 100 dollar in gems in KOC over the weekend but now I'm trying to purchase more and it gives me an error. Koc= kingdoms of Camelot

  • Pulling through the Variant description to the sales order

    Is there a way to change the material description in the sales order to match the Characteristic Value?  Is there an enhancement that may work?  Also, looking for an enhancement that will update the Equipment Master description based on the serial nu