Két tábla JOIN-olt lekérdezésben különböző ORDER-rel.
Sziasztok!
Sgítsetek nekem egy kicsit, nem értek valamit és kellene rá egy lekérdezést írnom:
Van két táblám pl.: emberek és esemenyek.
Az emberek táblában értelem szerűen emberek neveit tárolom az esemenyek táblában pedig az emberekhez tartozó eseményeket, azaz egy 1:n azonosított kapcsolatról beszélek.
Az események dátum szerint kerülnek bejegyzésre, itt egy klasszikus példa:
1 rekord az emberek táblában:
emberek_id: 1
emberek_nev: Minta Péter
Az előbb leírt rekordhoz tartozó 1. esemény az esemenyek táblában:
esemenyek_id: 1250
esemenyek_emberek_id: 1
esemeny_datuma: 1742
esemeny_leirasa: Születés
Az előbb leírt rekordhoz tartozó 2. esemény az esemenyek táblában:
esemenyek_id: 3500
esemenyek_emberek_id: 1
esemeny_datuma: 1770
esemeny_leirasa: Halálozás
Úgy kellene lekérdeznem, hogy az emberek kellenek és mindegyikhez az időben legutolsó esemény.
Ez majdnem jó, csak az események közül nem a legutolsóval tér vissza:
■ Sgítsetek nekem egy kicsit, nem értek valamit és kellene rá egy lekérdezést írnom:
Van két táblám pl.: emberek és esemenyek.
Az emberek táblában értelem szerűen emberek neveit tárolom az esemenyek táblában pedig az emberekhez tartozó eseményeket, azaz egy 1:n azonosított kapcsolatról beszélek.
Az események dátum szerint kerülnek bejegyzésre, itt egy klasszikus példa:
1 rekord az emberek táblában:
emberek_id: 1
emberek_nev: Minta Péter
Az előbb leírt rekordhoz tartozó 1. esemény az esemenyek táblában:
esemenyek_id: 1250
esemenyek_emberek_id: 1
esemeny_datuma: 1742
esemeny_leirasa: Születés
Az előbb leírt rekordhoz tartozó 2. esemény az esemenyek táblában:
esemenyek_id: 3500
esemenyek_emberek_id: 1
esemeny_datuma: 1770
esemeny_leirasa: Halálozás
Úgy kellene lekérdeznem, hogy az emberek kellenek és mindegyikhez az időben legutolsó esemény.
Ez majdnem jó, csak az események közül nem a legutolsóval tér vissza:
SELECT * FROM `enberek` JOIN `esemenyek` ON esemenyek.esemenyek_emberek_id = emberek.emberek_id GROUP BY esemenyek_emberek_id ORDER BY emberek_nev ASC, esemeny_datuma DESC
Sok megoldás
Egy kicsit segíts légyszi!
Kérlek segíts egy kicsit, kész vagyok az agyamra, egész nap ezt a nyamvadt lekérdezést feszegetem és teljesen belefásultam...
Most döbbentem rá, hogy még azt sem tudom lekérdezni, hogy az események táblában egy-egy ember azonosítóhoz milyen legnagyobb dátum tartozik, mert ha ezt mondom:
Gondolom a Subquery-ben ennek kellene szerepelnie, mondjuk úgy, hogy az esemeny_id-vel tér vissza és a fő lekérdezés azzal dolgozik:
SELECT * FROM esemenyek, WHERE id = (SELECT id FROM esemenyek WHERE adott id-hez tartozó MAX(esemeny_datuma))
order by + limit 1?
Miért is?
Egyébként ha a legutolsó eseményre lenne szükségem, én is ehhez hasonló lekérdezéssel kezdenék.
s_volenszki
jogos
Valami már lesz!
Hajtom tovább! :)
Köszi az ösztönzést!
ez biztosan rossz
Szerintem erre van szükséged: http://weblabor.hu/forumok/temak/17200.
Üdv,
Felhő
Igen az!
Igen valóban semmi garancia, sőt a tapasztalat szerint sosem egyezik! Vess egy óvatlan pillantást kérlek a #6 kommentemre!
Üdv,
s_volenszki
...
Az biztos, hogy az esemeny_id autoincrement, tehát a következő lekérdezés eredménye:
Ha ezt teszem meg subquery-nek:
Megint lendületet kaptam!
:)
És kész!
...
Nem teljesen értem.
Nem teljesen értem, valószínüleg az én tudásom hiányos, de mit jelent az az "e" ami a második subquery-t köti össze az eslő subquery group-jával?
e
Nem az igazi
Igen!
Köszi!
számított mező
Hú....
Ez annyira egyszerű, hogy már fáj! Hihetelen...
Köszi
teljesítmény
Üdv,
Felhő
teljesítmény?
ez kb. ugyanaz
Üdv,
Felhő
Egy kicsit megrémültem...
Nem hagytam figyelmen kívül azt ezt megelőző hozzászólásodban sem az általad javasolt esetet, de bevallom férfiasan, egy kicsit megrémültem tőle. Azt hiszem, a hétvégén egy csendes éjszakán átrágom rajta magam!
Köszönöm,
s_volenszki
magyarázat
A query alapvetően két részből áll. Mindkettő magjában ugyanaz a query áll: lekérdezzük a sorokat az adott rendezésnek megfelelően (nálad a dátum) úgy, hogy még a sorok mellé csapunk egy változót, ami szépen egyesével növekedik, és mindkét esetben ugyanahhoz a sorhoz ugyanaz az érték tartozik (mert a rendezés egyezik a két esetben).
Ezt követően az alsó részben elvégezzük a megfelelő csoportosítást (esetedben ember), majd kiválasztjuk a csoportből a számunkra szükséges sort (nálad ez az utolsó esemény, rendezéstől függően max/min rownum2).
Ezután jön a join, ami a csoportosítás alapját képző mező szerint végzünk. Ennek az eredménye, hogy minden egyes sorhoz egy olyan adat fog párosuli, ami azt mutatja, hogy az ő "kategóriájában" mi a kiválasztott rownum2 érték.
Mivel a rownum és a rownum2 szinkronban vannak, ezután már csak azokat a sorokat kell kiszűrnünk, ahol a pl. esetedben a kettő megegyezik.
Üdv,
Felhő
Nem egyszerű...
Köszönöm a magyarázatot.
Igazából megcsináltam és tökáletesen működik, de hazudnék ha azt mondanám, teljes egészében értem!
Így néz ki a legkérdezés, olyn nagy különbség nincs az általad gex-nek ajánlott meg ez között:
Tehát az tröténik, hogy az első sub-ban lekérdezem az összes eseményt dátumra csökkenő sorrendben, majd az inner join-nal, mint egy rekurzive, a második sub-ot végigtekeri újra az összes eseményen, de azt már úgy, hogy a sorszámozás után kizárólag a legnagyobb sorszámuval tér vissza.
Ekkor ott tartunk, hogy van egy olyan eredményünk, amiben annyiszor szerepelaz ember, ahány eseménye összesen van, de a JOIN-olt sub2 viselkedése miat, az összes eredménye ugyan úgy a legnagyobb sorszámú.
Ezt az eredményt GROUP-olom emberek_id-re és megvan amit kerestem...
Jaj, nem túl meggyőző...
s_volenszki
szerk:
Most vettem észre, ha kiveszem a GROUP-ot a végéről, akkor látom az összes találatot, és ami a lényeg, hogy a GROUP-olás előtt, olyan sorrendbe rendezi a lekérdezés eredményét, hogy a GROUP tulajdonsága, miszerint az elsővel tér vissza megfelelő ez elvárt adatokhoz képest, ugyanis olyan, mintha minde egyes létrejövő GROUP-nak lenne ORDER-e!
ORDER BY
pont az a lényeg :)
Üdv,
Felhő
Baj van, segítség!
Elég jól összeált ez a lekérdezés, szinte teljesen értem is, viszont van egy kis gond! Arról volt ugye szó, hogy a user változó
azaz, ha php-ból műveltetem az adatbázist, akkor az egy session-nek a mysql_query("") idézőjel közé írt művelete számit.
Az az én bajom, hogy Ha nem állítom be ezeket a változókat a konkrét lekérdezés elején, akkor NULL értéket kapok a sorszámok helyett mindenhol, épp úgy, ahogyan a lekérdezés eredményéül szolgáló legutolso_esemeny_sroszama_minden_emberhez is NULL lesz!
Próbáltam beletenni a lekérdezésbe vesszővel a SET-et de úgy szintaktikai hibát kapok. Van valakinek valami ötlete?
szerk:
Baromságot írtam, de csak azért gondolom, mert kipróbáltam, hogy a lekérdezés előtt két különálló mysql_query()-be beleraktarm a két user változó SET-jét és működik! Akkor most mi is a DB session? Mikor kezdődik és meddíg érvényes?
inicializálás
A fenti problémádra elég lenne egy if()-et használni, de szebb, ha minden esetben inicializálod a változókat, amit úgy tehetsz meg, hogy a FROM részhez hozzácsapod ezt: FROM (SELECT @rownum:=0) foo, ... .
Üdv,
Felhő
Értem.
Felmerült még egy kérdésem, bonyolódik a helyzet.
Igazából arra gondoltam, hogy majd ha ez a lekérdezés meglesz, akkor tovább jutok, de egyenlőre nem sikerült. Kérek még egy kicsi ösztönzést! :)
Az ezidági tárgyalt példa időközben kiegészült, azaz:
Az emberek táblából lekérdezni az összes embert, úgy, hogy hozzá legyen kötve az épp adott emberrel történt legutolsó esemény. Ez ugye fordult egy kicsit, mert az esmények táblában található távoli kulcs alapján (ami az ember azonosítója), megszerezzük a legutolsó eseményeket és a hozzájuk tartozó ember azonosítót, majd hozzákötöm az emberek táblát ezen a ponton:
Megpróbáltam a lekérdezés végén JOIN-olni, de azt az erdményt kapom mindíg, hogy
Már szinte minden variációt kipróbáltam. Betettem a sub-okba is, nem jártam eredménnyel.
Ha logikusan gondolkozom, csak akkor kötöm hozzá a felhasználó táblát, ha már minden végleges adat megvan. Már arra is gondoltam, hogy elkezdem az egész lekérdezést azzal, hogy kiválasztok minden felhasználót a felhasználük táblából, hozzáközöm az egész jelenlegi lekérdezést és a végén az ON kitételben azt mondom, ahol felhasznalo.felhasznaloid = emberek.user_id.
Kérek véleményt mielőtt padlóra küldöm az sql szervert!
s_volenszki