减去运行总计直到0

时间:2018-12-19 16:17:59

标签: sql oracle case running-total

我正在设法对avail_relief_amt列进行减法运算。目标是使(qty_filled / qty_total)尽可能接近100%,这就是room_to_improve列的作用。

当前查询:

    SELECT
    t2_date,
    part_no,
    issue_group,
    level,
    p_category,
    qty_filled,
    qty_total,
    relief_amt,
    curr_mth_note,
    carryover_note,
    room_to_improve,
    avail_relief_amt,
    CASE
        WHEN avail_relief_amt != 0 THEN ( qty_total - room_to_improve )
        ELSE NULL
    END AS new_qty_total
FROM
    (
        SELECT
            t2_date,
            part_no,
            issue_group,
            level,
            p_category,
            qty_filled,
            qty_total,
            relief_amt,
            curr_mth_note,
            carryover_note,
            CASE
                WHEN qty_filled < qty_total THEN ( qty_total - qty_filled )
                ELSE NULL
            END AS room_to_improve,
            avail_relief_amt
        FROM
            (
                SELECT
                    t2_date,
                    part_no,
                    issue_group,
                    level,
                    p_category,
                    qty_filled,
                    qty_total,
                    relief_amt,
                    curr_mth_note,
                    carryover_note,
                    CASE
                        WHEN curr_mth_note IS NOT NULL THEN relief_amt
                        ELSE NULL
                    END AS avail_relief_amt
                FROM
                    (
                        SELECT
                            t1.t2_date,
                            t1.part_no,
                            t1.issue_group,
                            t1.level,
                            t1.p_category,
                            t1.qty_filled,
                            t1.qty_total,
                            mv.relief_amt,
                            mv.curr_mth_note,
                            mv.carryover_note
                        FROM
                            table_detail_mv mv,
                            table_part_con t1
                        WHERE
                            t1.part_no = mv.part_no
                            AND t1.t2_date = mv.t2_date
                        GROUP BY
                            t1.t2_date,
                            t1.issue_group,
                            t1.level,
                            t1.part_no,
                            t1.p_category,
                            t1.qty_filled,
                            t1.qty_total,
                            mv.relief_amt,
                            mv.curr_mth_note,
                            mv.carryover_note
                        ORDER BY
                            t1.t2_date,
                            t1.issue_group,
                            t1.level DESC
                    )
            )
    )
ORDER BY
    t2_date,
    part_no,
    issue_group,
    level DESC

当前输出:

enter image description here

avail_relief_amt列以relief_amt列中的任何数字开头。如果avail_relief_amt > room_to_improve,下一个avail_relief_amt应该是(avail_relief_amt - room_to_improve)剩下的值。在我上面的输出中,由于第2行没有room_to_improve,所以它需要下降到下一行,依此类推,直到avail_relief_amt = 0

所需的输出:

enter image description here

编辑

我从上面的查询中删除了room_to_improveavail_relief_amtnew_qty_total列,因为它们只是出于帮助可视化最终目标的想法而添加的。

当前输出(没有上面的列):

enter image description here

更好地解释最终目标:

  • 通过将qty_total取为等于0,使qty_filled / relief_amt尽可能接近100%。
  • relief_amt将沿优先级下降(忽略“后期”)。 优先顺序为(issue_group='1', s_level='80'-(issue_group='1', s_level='100')-(issue_group='2/3 ', s_level='80')-(issue_group='2/3 ', s_level='100'
  • 使用上面的输出,需要27个才能制作qty_total = qty_filled,因此该数字将从relief_amt(共57个)中删除。离开relief_amt=30
  • 然后,查询将跳至下一个优先级,但是由于94 = 94,因此不需要使用relief_amt,因此它会跳至下一行(请记住跳过“ Late”)。
  • 现在我们需要使qty_total=226靠近qty_filled=125,但是我们只有relief_amt=30。因此,剩下的relief_amt是从该qty_total=226中提取出来的,成为新的qty_total=196,然后我们就离开了relief_amt

我知道这非常令人困惑,并且由于正在进行的所有变量和重复方程式,我和我的同事们非常沮丧。

任何帮助都会很棒!

1 个答案:

答案 0 :(得分:0)

我有一个解决方案,但是由于您没有原始数据,因此我的解决方案使用您的查询作为视图。

因此,您必须使用以下语法创建视图:

create view currentOutput as select ...your current query here... ;

此外,您还需要一个日期字段,我认为该字段将被命名为dateEntry

然后您可以执行以下操作:

 SELECT dateEntry,
       room_to_improve,
       CASE
           WHEN temp.AVAIL_RELIEF_AMT - NVL(SUMPREVIOUSROOMTOIMPROVE, 0) < 0 THEN 0
           ELSE temp.AVAIL_RELIEF_AMT - NVL(SUMPREVIOUSROOMTOIMPROVE, 0)
       END AS AVAIL_RELEIF_AMT,
       new_qty_total
FROM
  ( SELECT c1.*,

     (SELECT sum(room_to_improve)
      FROM currentOutput
      WHERE dateEntry < c1.dateEntry) AS sumPreviousRoomToImprove
   FROM currentOutput c1
   ORDER BY dateEntry )TEMP ;

结果:

DATEENTRY -ROOM_TO_IMPROVE-   AVAIL_RELEIF_AMT-   NEW_QTY_TOTAL-
1-    27  -57-    67
2-        -30-    
3-    101-    -30-    125
4-    49- 0-  177-

提琴:https://dbfiddle.uk/?rdbms=oracle_11.2&fiddle=2c074fe2adc232fd596d623e1cee8123