2009-03-03 3 views
0

Wie Sie einen Mitarbeiter holen, sagen 5 letzten Action_reason Zeilen, die in einem effektiven datierten Datensatz, keine zukünftigen Zeilen sind, sollten nur aktuelle und Verlaufszeilen auswählen (effektives Datum < = sysdate). Kann ich diese in einer Zeile holen oder sind es 5 Zeilen für einen Mitarbeiter?Arbeiten mit effektiven datierten Aufzeichnungen

select emplid, effdt, action_reasons 
-- we have to build a logic here. 
-- Should we initialize 5 ACT variables to fetch rows into it? 
-- Please help 
from JOB 
where emplid = '12345' 
    and effdt <= sysdate. 
+0

Warum möchten Sie eine einzelne Zeile? Was willst du in den Zeilen für Leute mit nur 4 Aktionsgrundzeilen? 3, 2, 1, 0? Wäre es nicht besser, einen Tisch mit 0 bis 5 Zeilen pro Mitarbeiter zu haben, wie es die Lösung von @ Quassnoi vorsieht? –

+0

0 und 5 Zeilen holen die 5 letzten Zeilen eines Mitarbeiters, aber der Aktionsgrund könnte der gleiche sein. Ich möchte 5 neue Aktionsgründe holen; Wenn sie nur 2-3 geänderte Reihen haben, dann werden die anderen zwei leer sein. Und dies dient dem Zweck der Berichterstattung. –

Antwort

3
SELECT LTRIM(SYS_CONNECT_BY_PATH(emplid || ', ' || effdt || ', ' || action_reasons, ', '), ', ') 
FROM (
     SELECT 
     FROM (
      SELECT emplid, effdt, action_reasons, ROW_NUMBER() OVER (ORDER BY effdt) AS rn 
      FROM JOB 
      WHERE emplid= '12345' 
       AND effdt <= SYSDATE 
      ) 
     WHERE rn <= 5 
     ) 
WHERE CONNECT_BY_ISLEAF = 1 
START WITH 
    rn = 1 
CONNECT BY 
    rn = PRIOR rn + 1 
+0

Wie bekomme ich den Mitarbeiter (nehme 5 Aktionen an) in einer Zeile von letzten bis letzten Aktionen mit entsprechenden effdts, aber nicht die letzten 5 Zeilen vom Job –

+0

Sorry, ich bekomme nicht ganz was du willst. Bitte posten Sie einige Beispieldaten und das gewünschte Ergebnis in Ihrer Frage. – Quassnoi

+0

Er will: emplid, effdt1, act1, effdt2, act2, effdt3, act3, ...; das ist natürlich keine besonders gute Idee. –

0
SELECT JOBXX.EMPLID,JOBXX.EFFDT,JOBXX.ACT1,JOBXX.ACT2,JOBXX.ACT3,JOBXX.ACT4,JOBXX.ACT5 
FROM 
    (SELECT SD.EMPLID, 
      SD.EFFDT, 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 1 THEN SD.A1 ELSE 0 END)),1,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 1 THEN SD.A1 ELSE 0 END)),3,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 1 THEN SD.A1 ELSE 0 END)),5,2)) 
      AS ACT1, 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 2 THEN SD.A1 ELSE 0 END)),1,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 2 THEN SD.A1 ELSE 0 END)),3,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 2 THEN SD.A1 ELSE 0 END)),5,2)) 
      AS ACT2, 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 3 THEN SD.A1 ELSE 0 END)),1,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 3 THEN SD.A1 ELSE 0 END)),3,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 3 THEN SD.A1 ELSE 0 END)),5,2)) 
      AS ACT3, 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 4 THEN SD.A1 ELSE 0 END)),1,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 4 THEN SD.A1 ELSE 0 END)),3,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 4 THEN SD.A1 ELSE 0 END)),5,2)) 
      AS ACT4, 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 5 THEN SD.A1 ELSE 0 END)),1,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 5 THEN SD.A1 ELSE 0 END)),3,2)) || 
      CHR(SUBSTR(TO_CHAR(SUM(CASE WHEN SD.R3 = 5 THEN SD.A1 ELSE 0 END)),5,2)) 
      AS ACT5 
    FROM (
     SELECT EMPLID,EFFDT,ACTION_REASON, 
       SUBSTR(ACTION_REASON,1,1), 
       SUBSTR(ACTION_REASON,2,1), 
       SUBSTR(ACTION_REASON,3,1), 
       TO_NUMBER(ASCII(SUBSTR(ACTION_REASON,1,1)) || 
       ASCII(SUBSTR(ACTION_REASON,2,1)) || 
       ASCII(SUBSTR(ACTION_REASON,3,1))) AS A1, 
       ROW_NUMBER() over(PARTITION BY EMPLID,EFFDT ORDER BY EFFDT desc,EFFSEQ desC) R3 
     FROM PS_JOB 
     WHERE action in ('ABC','XYZ') 
     and action_reason in ('123','456','789') 
     and emplid IN('12345','ABCDE') 
     AND effdt between '01-jan-2008' and '18-dec-2008' 
     ORDER BY EFFDT DESC, EFFSEQ DESC 
    ) SD       
    GROUP BY EMPLID , EFFDT    
) JOBXX 
0

können Sie die Daten haben jede mögliche Weise, die Sie wünschen. Wenn Sie es als fünf Zeilen möchten, dann können Sie diese verwenden:

select * from (
      select emplid, empl_rcd, effdt, action_reason 
        , rank() over (partition by emplid, empl_rcd 
           order by effdt desc, effseq desc) rank1 
       from ps_job 
       where emplid = '12345' 
       and effdt <= sysdate) 
where rank1 <= 5 

Wenn Sie die Daten alle auf einer einzelnen Zeile wollen, dann Oracle LAG analytische Funktion verwenden, also:

select * from ( 
    select emplid, empl_rcd, effdt 
     , lag(effdt) over(partition by emplid, empl_rcd order by effdt, effseq) effdt_lag1 
     , lag(effdt, 2) over(partition by emplid, empl_rcd order by effdt, effseq) effdt_lag2 
     , lag(effdt, 3) over(partition by emplid, empl_rcd order by effdt, effseq) effdt_lag3 
     , lag(effdt, 4) over(partition by emplid, empl_rcd order by effdt, effseq) effdt_lag4 
     , action_reason 
     , lag(action_reason) over(partition by emplid, empl_rcd order by effdt, effseq) action_reason_lag1 
     , lag(action_reason, 2) over(partition by emplid, empl_rcd order by effdt, effseq) action_reason_lag2 
     , lag(action_reason, 3) over(partition by emplid, empl_rcd order by effdt, effseq) action_reason_lag3 
     , lag(action_reason, 4) over(partition by emplid, empl_rcd order by effdt, effseq) action_reason_lag4 
     from ps_job 
    where emplid = '12345') j 
where effdt = (
      select max(j1.effdt) from ps_job j1 
      where j1.emplid = j.emplid 
       and j1.empl_rcd = j.empl_rcd 
       and j1.effdt <= sysdate) 

dies die letzte gibt 5 Effdt-Werte und die letzten 5 Aktionsgrundwerte. Wenn Sie beide nicht benötigen, kann das obige SQL entsprechend getrimmt werden.

Verwandte Themen