2009-11-04 16 views
6

Znam tytuł nie brzmi bardzo opisowy, ale to najlepsze co mogłem myśleć:Wiele wartości max w zapytaniu

mam ten stół

 
ID  BDATE  VALUE 
28911 14/4/2009 44820 
28911 17/4/2009 32240 
28911 20/4/2009 30550 
28911 22/4/2009 4422587,5 
28911 23/4/2009 4441659 
28911 24/4/2009 7749594,67 
38537 17/4/2009 58280 
38537 20/4/2009 137240 
38537 22/4/2009 81098692 
38605 14/4/2009 2722368 
38605 20/4/2009 5600 
38605 22/4/2009 1625400 
38605 23/4/2009 6936575 

która w rzeczywistości jest to bardzo skomplikowane zapytanie zamknięte w widoku, ale teraz nie jest to już kwestią podstawową.

Chciałbym mieć dla każdego ID, wiersz zawierający najwyższy BDate. W tym przykładzie byłby to wynik.

 
ID  BDATE  VALUE 
28911 24/4/2009 7749594,67 
38537 22/4/2009 81098692 
38605 23/4/2009 6936575 

Próbowałem już

select id, max(bdate), value from myview group by id, value 

ale następnie zwraca wszystkie wiersze, bo każda wartość collumn jest inna. Ta kwerenda została zaprojektowana w Oracle v10 i mam prawo używać tylko wybranych zapytań, a nie tworzyć procedur.

+0

dzięki za wszystko odpowiada facetom. – kurast

+0

diablo II - doki kurastyczne? – CheeseConQueso

+0

Tak, nazywam się z Diablo II. doki Kurasta. Słowo Kurast, gdy wymawiane dźwięki są dla mnie tak niesamowite, że nie mogłem znieść ich użycia. – kurast

Odpowiedz

10
select id, bdate, value 
from myview 
where (id, bdate) in 
    (select id, max(bdate) 
    from myview group by id) 
/
+0

Jak dodać do tego zapytania inny warunek - np. "ORAZ wartość> 500"? – kerosene

0
select a.* from myview a, (select id, max(bdate) from myview group by id) b 
where a.id = b.id and a.bdate = b.bdate 
+0

nie zwraca wartości kolumny, którą chcę – kurast

+0

Naprawiono. Oczywiście niewytłumaczone. –

0
SELECT id, bdate, value FROM myview 
WHERE (id, bdate) IN (SELECT id, MAX(bdate) FROM myview GROUP BY id) 

(niesprawdzone ... Nie mam teraz dostępne Oracle ...)

2

Można użyć Analytics:

select 
     id, bdate, value 
    from 
     (
     select 
      id, bdate, value, max(bdate) over (partition by id) max_bdate 
     from 
      myview 
    ) 
    where 
     bdate = max_bdate 
2

Można użyć INNER JOIN, aby odfiltrować tylko maksymalne rzędy:

select t.* 
from YourTable t 
inner join (
    select id, max(bdate) as maxbdate 
    from YourTable 
    group by id 
) filter 
    on t.id = filter.id 
    and t.bdate = filter.maxbdate 

Drukuje:

id  bdate  value 
38605 2009-04-23 6936575 
38537 2009-04-22 81098692 
28911 2009-04-24 7749594.67 

Należy zauważyć, że ten powróci wiele rzędów dla identyfikatora, który ma wiele wartości tego samego bdate.

8

można użyć MAX...KEEP(DENSE_RANK FIRST...) konstrukt:

SQL> SELECT ID, 
    2   MAX(bdate) bdate, 
    3   MAX(VALUE) KEEP(DENSE_RANK FIRST ORDER BY bdate DESC) VALUE 
    4 FROM DATA 
    5 GROUP BY ID; 

     ID BDATE   VALUE 
---------- ----------- ---------- 
    28911 24/04/2009 7749594,67 
    38537 22/04/2009 81098692 
    38605 23/04/2009  6936575 

to będzie tak skuteczny jak metody analityki sugerowanej przez Majkel (bez samosprzężenie, jeden przejazd na dane)

Powiązane problemy