Raggruppa per unendo due volte lo stesso tavolo
Domanda
Sto scrivendo una query per riassumere alcuni dati. Ho una bandiera nella tabella che è sostanzialmente booleana, quindi ho bisogno di alcune somme e conteggi basati su un valore di esso, e quindi la stessa cosa per l'altro valore, in questo modo:
select
location
,count(*)
,sum(duration)
from my.table
where type = 'X'
and location = @location
and date(some_tstamp) = @date
group by location
E poi lo stesso per un altro valore della colonna type. Se mi unisco a questa tabella due volte, come posso ancora raggruppare in modo da poter ottenere solo aggregazione per ogni tabella, ovvero contare (a. *
) invece di contare (*) ...
Sarebbe meglio scrivere due query separate?
Modifica
Grazie a tutti, ma non intendevo questo. Devo ottenere un riepilogo in cui type = 'X' e un riepilogo in cui type = 'Y' separatamente ... fammi pubblicare un esempio migliore. Quello che intendevo era una domanda come questa:
select
a.location
,count(a.*)
,sum(a.duration)
,count(b.*)
,sum(b.duration)
from my.table a, my.table b
where a.type = 'X'
and a.location = @location
and date(a.some_tstamp) = @date
and b.location = @location
and date(b.some_tstamp) = @date
and b.type = 'Y'
group by a.location
Cosa devo raggruppare? Inoltre, a DB2 non piace contare (a. *
), è un errore di sintassi.
Soluzione
select
location
,Sum(case when type = 'X' then 1 else 0 end) as xCount
,Sum(case when type = 'Y' then 1 else 0 end) as YCount
,Sum(case when type = 'X' then duration else 0 end) as xCountDuration
,Sum(case when type = 'Y' then duration else 0 end) as YCountDuration
from my.table
where
location = @location
and date(some_tstamp) = @date
group by location
Questo dovrebbe funzionare in SQL Server. Immagino che db2 dovrebbe avere qualcosa di simile.
Modifica: aggiungi una condizione where per limitare i record per selezionare type = X o type = Y, se " type " può avere un valore diverso da X e Y.
Altri suggerimenti
Il tuo esempio con il join non ha molto senso. Stai facendo un prodotto cartesiano tra A e B. È davvero quello che vuoi?
Di seguito troverai count (*) e sum (duration) per ogni coppia che soddisfa la clausola WHERE. Sulla base della tua descrizione, questo suona come quello che stai cercando:
select
type
,location
,count(*)
,sum(duration)
from my.table
where type IN ('X', 'Y')
and location = @location
and date(some_tstamp) = @date
group by type, location
Per far funzionare i conteggi, invece di count (a. *) basta contare (a.location) o qualsiasi altra colonna non nulla (il PK sarebbe l'ideale).
Per quanto riguarda la domanda principale, una delle risposte fornite da Shahkalpesh o George Eadon sopra avrebbe funzionato. Non vi è motivo in questo esempio di unirsi due volte alla tabella.