2016-05-25 4 views
1

Ich habe eine Tabelle in Oracle 10g DB-Engine, die Aufzeichnungen von Service-Operationen enthält. Die Anforderung besteht darin, die Verarbeitungszeit jeder Serviceanforderung zu berechnen. Jede Dienstanforderung kann mehrere Datensätze erzeugen, von denen jeder einen Schritt in dem Prozess darstellt. Also habe ich eine Tabelle mit den folgenden Spalten:Wie kann ich mithilfe von Oracle SQL Datensätze gruppieren und Berechnungen zwischen den ersten und letzten Datensätzen in jeder Gruppe durchführen?

ID 
CREATED_ON 
SERVICE_OPERATION 
RESULT 
FK_SERVICE_REQUEST_ID 

wo die letzte Spalte die Kennung der Serviceanforderungen ist.

Wie kann ich den Unterschied zwischen CREATED_ON des ersten und letzten Datensatzes in jeder durch FK_SERVICE_REQUEST_ID identifizierten Gruppe berechnen? Bin ich besser dran:

SELECT FK_SERVICE_REQUEST_ID, CREATED_ON, SERVICE_OPERATION, RESULT FROM TABLE ORDER BY FK_SERVICE_REQUEST_ID, ID; 

und ein paar Tricks in Excel? Wenn ja, wie kann ich dies in Excel erreichen?

+0

Was ist das Feld, das die Reihenfolge der Datensätze bestimmt, den ersten und letzten Datensätze zu bestimmen? Ordnen wir nach der ID, wobei die kleinste Nummer der "erste" Datensatz und die größte Nummer der "letzte" Datensatz ist? – Lock

+0

Nun ID sollte ziemlich stabil sein. Ich kann mir kein Szenario vorstellen, in dem ein späterer Schritt mit einem späteren Zeitstempel mit einer niedrigeren ID generiert würde. – Max

Antwort

1
SELECT 
    FK_SERVICE_REQUEST_ID, 
    MIN(CREATED_ON) MIN_DT, 
    MAX(CREATED_ON) MAX_DT, 
    MAX(CREATED_ON)-MIN(CREATED_ON) PROC_TIME 
FROM TABLE 
GROUP BY 
    FK_SERVICE_REQUEST_ID 
ORDER BY 
    FK_SERVICE_REQUEST_ID; 
+0

Das sind die Max und Min, er wollte das erste und letzte! – sagi

+0

@sagi - Wie unterscheiden sich Min- und Max-Daten von den ersten und letzten Daten? –

+0

Vielleicht ist es mein schlechtes. Max und Min sind die ersten und letzten in Bezug auf Zeitstempel. – Max

0

Sie können ROW_NUMBER() für diesen Einsatz:

SELECT s.FK_SERVICE_REQUEST_ID, 
     MAX(CASE WHEN s.asc_rnk = 1 THEN CREATED_ON END) as first_crt_on, 
     MAX(CASE WHEN s.asc_rnk = 1 THEN SERVICE_OPERATION END) as first_srv_op, 
     MAX(CASE WHEN s.desc_rnk = 1 THEN CREATED_ON END) - 
     MAX(CASE WHEN s.asc_rnk = 1 THEN CREATED_ON END) as diff_dates 
FROM (
    SELECT t.*, 
      ROW_NUMBER() OVER(PARTITION BY t.FK_SERVICE_REQUEST_ID BY t.CREATED_ON) as asc_rnk, 
      ROW_NUMBER() OVER(PARTITION BY t.FK_SERVICE_REQUEST_ID BY t.CREATED_ON DESC) as desc_rnk 
    FROM YourTable t) s 
GROUP BY s.FK_SERVICE_REQUEST_ID 

I CREATED_ON als Auftragsteil verwendet, wenn seine durch eine andere Spalte, ändern. Ich benutzte auch die FK_SERVICE_REQUEST_ID Spalte als die Gruppen, wusste nicht, ob es das ist oder ID

0

Analitische Funktion. last_VALUE und FIRST_VALUE haben das Standard-Abfragefenster RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW. In diesem Fall möchten wir von der ersten bis zur letzten Zeile im Fenster prüfen. Um dies zu erreichen Ich habe RANGE BETWEEN CURRENT ROW AND UNBOUNDED FOLLOWING hinzugefügt

with tabl as (
select 1 FK_SERVICE_REQUEST_ID, sysdate -10 CREATED_ON,1 idn from dual 
union 
select 1 FK_SERVICE_REQUEST_ID, sysdate -15 CREATED_ON ,2 from dual 
union 
select 1 FK_SERVICE_REQUEST_ID, sysdate -20 CREATED_ON,3 from dual 
union 
select 2 FK_SERVICE_REQUEST_ID, sysdate -3 CREATED_ON,4 from dual 
union 
select 2 FK_SERVICE_REQUEST_ID, sysdate -5 CREATED_ON,5 from dual 
union 
select 2 FK_SERVICE_REQUEST_ID, sysdate -1 CREATED_ON,6 from dual) 
select FK_SERVICE_REQUEST_ID, min(last_d-first_d) from (
SELECT IDn,FK_SERVICE_REQUEST_ID, CREATED_ON 
    ,FIRST_VALUE(CREATED_ON) OVER (partition by FK_SERVICE_REQUEST_ID ORDER BY CREATED_ON ASC ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS first_d 
    ,last_VALUE(CREATED_ON) OVER (partition by FK_SERVICE_REQUEST_ID ORDER BY CREATED_ON ASC ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING) AS last_d 
    from tabl) 
    group by FK_SERVICE_REQUEST_ID; 
Verwandte Themen