sql >> データベース >  >> RDS >> Oracle

値が変更されない場合にのみ日付レコードを折りたたむ-OracleSQL

    これは少し複雑に思えるので、改善に興味があります。

    select distinct emp_id,
        nvl(x_start_date,
            lag(x_start_date)
                over (partition by emp_id
                    order by rn)) as start_date,
        nvl(x_end_date,
            lead(x_end_date)
                over (partition by emp_id
                    order by rn nulls first))
                        as end_date,
            rating,
            department
    from (
        select emp_id, start_date, end_date, rating, department,
            case start_date
                when lag(end_date)
                    over (partition by emp_id, rating, department
                        order by start_date) then null
                else start_date end as x_start_date,
            case end_date
                when lead(start_date)
                    over (partition by emp_id, rating, department
                        order by start_date) then null
                else end_date end as x_end_date,
            rownum as rn
        from table1
    )
    where x_start_date is not null or x_end_date is not null
    order by emp_id, start_date
    /
    

    このテストデータの場合:

        EMP_ID START_DA END_DATE RA DEPARTMENT               SALARY
    ---------- -------- -------- -- -------------------- ----------
          2000 01012010 01012011 A  HR                         9000
          2000 01012011 01012012 A  HR                        10000
          2000 01012012 01012013 A+ HR                        20000
          2000 01012013 01012014 A  HR                        20000
          2000 01012014 12319999 A  HR                        21000
          3000 01012011 01012012 B  Operations                50000
          3000 01012012 12319999 B  Operations                60000
          4000 07012011 07012012 B  Operations                50000
          4000 07012012 07012013 B  Operations                50000
          4000 07012013 12319999 B  Operations                60000
    

    私はこれを手に入れました:

        EMP_ID START_DA END_DATE RA DEPARTMENT
    ---------- -------- -------- -- --------------------
          2000 01012010 01012012 A  HR
          2000 01012012 01012013 A+ HR
          2000 01012013 12319999 A  HR
          3000 01012011 12319999 B  Operations
          4000 07012011 12319999 B  Operations
    

    emp_idも試してみました (4000 )3つの連続した日付範囲があり、それを処理しました-外側のwhere 節は、本質的に、中間エントリを非表示にします。 編集して追加2000/Aの追加の日付範囲でも機能するようになりました 、外側のleadの順序を修正したので /lag パーティション。

    内側のクエリは、連続するブロックの最初の開始日と最後の終了日を除くすべてを空白にし、外側のクエリは2回目のleadを使用します。 およびlag それらを同一の行にマージします。これはdistinct その後崩壊します。

    start_dateを想定しています およびend_date DATEです VARCHAR2ではなくフィールド 、NLS_DATE_FORMATがあります MMDDYYYYに設定 。文字列として保存されている場合(これは悪い考えです)、to_date()が必要です。 注文を適切に機能させるために、かなりの数の場所で。



    1. 入れ子集合を使用して動的メニューを作成する

    2. MySQLはhtmlデータまたはPHPから平文を抽出しますか?

    3. ORA-12571:TNSパケット・ライターの障害とORA-03135:接続が接続を失いました。

    4. MySQLGroupByおよび水平方向に表示