2015-06-03 15 views
5

MODIFICA: Rifare l'intera domanda. Lo portò nel modo sbagliato la prima volta.CAS-T-SQL Controllare la data più recente e poi gli altri valori

I Risultati dovrebbero essere come:

MachineName | OrderNo | TaskID | Code | NettoProd | BrutoProd | DiffProd 
========================================================================= 
F1   123456 101  O  100000  125000  25000 
F1   123456 102  P8  1000000  1250000  250000 
F1   123456 103  P1  10000  12500  2500 
F1   123456 104  P4  100000  125000  25000 

Il JobSummary ha le seguenti colonne:

StartDate 
TaskID 

Il Route ha le seguenti colonne:

OrderNo 
TaskID 

Il Resource contiene i dati sulle macchine

MachineID 

ho già aggiunto la parte di Kyle Gobel, che era la risposta corretta, se avessi fornito tutti i dettagli, in primo luogo.

Quello che vorrei realizzare è quello di mostrare un O quando è la prima taskID dei compiti connessi ad uno OrderNo basato sul StartDate, che è un campo DateTime nella tabella.

Se è impossibile controllare sia Route.No e JobSummary.StarDate in una CASE dichiarazione, poi una colonna separata per entrambi farà troppo.

Query

SELECT Resource.DESCRIPTION AS MachineName 
    ,Route.OrderNo 
    ,Route.TaskID 
    ,CASE 
     WHEN JobSummary.StartDate = (SELECT MIN(cr.StartDate) FROM JobSummary cr) THEN 'O' 
     WHEN Route.No = 1 OR Route.No = 2 THEN 'P1' 
     WHEN Route.No = 4 THEN 'P4' 
     WHEN Route.No >= 8 THEN 'P8' 
     ELSE '*FP*' 
    END AS Code 
    ,JobSummary.GoodProd As NettoProd 
    ,JobSummary.GoodProd + JobSummary.SetupProd + JobSummary.WasteProd As BrutoProd 
    ,(JobSummary.SetupProd + JobSummary.WasteProd) As DiffProd 

FROM Route 
JOIN Resource ON Resource.MachineID = Route.MachineID 
JOIN JobSummary ON JobSummary.TaskID = Route.TaskID AND JobSummary.MachineID = Route.MachineID 
+1

Se potessi darci la domanda, cosa non funziona e i risultati attesi, molto probabilmente otterresti una buona risposta. –

+2

Non vedo alcun riferimento a StartDate o al codice 'O' nell'esempio sopra; puoi pubblicare un esempio più completo di ciò che stai cercando di fare? –

risposta

3

È possibile utilizzare ROW_NUMBER() con PARTITION BY per identificare il primo record taskID in base alla sua StartDate per un OrderNo come questo ROW_NUMBER()OVER(PARTITION BY Route.OrderNo ORDER BY JobSummary.StartDate ASC

Esempio Dati e struttura

CREATE TABLE [JobSummary] (MachineID INT,TaskID INT,StartDate DATETIME,GoodProd NUMERIC(18,0),SetupProd NUMERIC(18,0),WasteProd NUMERIC(18,0)); 
CREATE TABLE [Route] (OrderNo INT,MachineID INT,TaskID INT,[No] INT); 
CREATE TABLE [Resource] (MachineID INT,DESCRIPTION CHAR(2)); 


INSERT INTO [Resource] VALUES(1,'F1'); 

INSERT INTO [Route] VALUES(123456,1,101,1); 
INSERT INTO [Route] VALUES(123456,1,102,9); 
INSERT INTO [Route] VALUES(123456,1,103,2); 
INSERT INTO [Route] VALUES(123456,1,104,4); 

INSERT INTO [JobSummary] VALUES(1,101,'20150101',100000,20000,5000); 
INSERT INTO [JobSummary] VALUES(1,102,'20150103',1000000,200000,50000); 
INSERT INTO [JobSummary] VALUES(1,103,'20150102',10000,2000,500); 
INSERT INTO [JobSummary] VALUES(1,104,'20150103',100000,20000,5000); 

Query

;WITH CTE AS 
(
SELECT Route.No 
    ,Resource.[DESCRIPTION] AS MachineName 
    ,Route.OrderNo 
    ,Route.TaskID 
    ,JobSummary.GoodProd As NettoProd 
    ,JobSummary.GoodProd + JobSummary.SetupProd + JobSummary.WasteProd As BrutoProd 
    ,(JobSummary.SetupProd + JobSummary.WasteProd) As DiffProd 
    ,ROW_NUMBER()OVER(PARTITION BY Route.OrderNo ORDER BY JobSummary.StartDate ASC) rn 
FROM Route 
JOIN Resource ON Resource.MachineID = Route.MachineID 
JOIN JobSummary ON JobSummary.TaskID = Route.TaskID AND JobSummary.MachineID = Route.MachineID 
) 
SELECT 
    MachineName, 
    OrderNo, 
    TaskID, 
    CASE 
     WHEN rn = 1 THEN 'O' 
     WHEN No IN (1,2) THEN 'P1' 
     WHEN No = 4 THEN 'P4' 
     WHEN No >= 8 THEN 'P8' 
     ELSE '*FP*' 
    END AS Code, 
    NettoProd, 
    BrutoProd, 
    DiffProd 
FROM CTE 
ORDER BY OrderNo,TaskID 

uscita

MachineName OrderNo TaskID Code NettoProd BrutoProd DiffProd 
F1 123456 101 O 100000 125000 25000 
F1 123456 102 P8 1000000 1250000 250000 
F1 123456 103 P1 10000 12500 2500 
F1 123456 104 P4 100000 125000 25000 

SQL Fiddle

+0

Non l'avrei mai scoperto da solo. Andando a studiare la partizione su internet. Grazie. – Ignotus

2

Dalla lettura alla tua domanda, si potrebbe essere alla ricerca per la funzione di aggregazione min.

case 
    when route.startDate = (select min(r.startdate) from table r) then 'O' 
    when route.no = 1 or route.no = 2 then 'P1' 
    .... 
end as code 
1

Utilizzando ROW_NUMBER può essere un buon punto di partenza qui, ma come si desidera controllare solo per il primo StartDate, può essere una migliore idea di utilizzare invece MIN() OVER.La query postato avrebbe bisogno solo di un piccolo cambiamento (sottolineato):

SELECT Resource.DESCRIPTION AS MachineName 
    ,Route.OrderNo 
    ,Route.TaskID 
    ,CASE 
     WHEN JobSummary.StartDate = MIN(JobSummary.StartDate) OVER (PARTITION BY Route.OrderNo) THEN 'O' 
     WHEN Route.No = 1 OR Route.No = 2 THEN 'P1' 
     WHEN Route.No = 4 THEN 'P4' 
     WHEN Route.No >= 8 THEN 'P8' 
     ELSE '*FP*' 
    END AS Code 
    ,JobSummary.GoodProd As NettoProd 
    ,JobSummary.GoodProd + JobSummary.SetupProd + JobSummary.WasteProd As BrutoProd 
    ,(JobSummary.SetupProd + JobSummary.WasteProd) As DiffProd 

FROM Route 
JOIN Resource ON Resource.MachineID = Route.MachineID 
JOIN JobSummary ON JobSummary.TaskID = Route.TaskID AND JobSummary.MachineID = Route.MachineID 
;

Forse la partizione avrebbe bisogno di includere Resource.DESCRIPTION così - difficile dire da un piccolo esempio.

La query sopra potrebbe funzionare più rapidamente del metodo ROW_NUMBER. Questo perché con ROW_NUMBER i sottoinsiemi dovrebbero essere ordinati completamente, mentre MIN() OVER cercherebbe solo un singolo valore da ogni sottoinsieme.

D'altra parte, se è possibile che in un secondo momento occorra una condizione speciale per una seconda, terza riga ecc., Il metodo ROW_NUMBER sarebbe sicuramente più flessibile in questo senso.

Problemi correlati