04. september 2013 - 23:27Der er
9 kommentarer og 1 løsning
SQL unike poster fra tabel1, hvis relationer findes i tabel2
Hej gutter,
Jeg har to tabeller:
Poster: id overskrift tekst
Billeder: id post_id sti filnavn prioritet
Jeg har brug for et resultset hvor jeg får top 3 Poster (sorteret efter id DESC) som har billeder tilknyttet (og her skal jeg bruge det først billede, sorteret efter prioritet i billedetabellen):
Dvs. der skal være følgende i resultsettet: id,overskrift,tekst,sti,filnavn
Tak for svaret Christian_Belgien :) Desværre er det ikke løsningen, da en alm. JOIN i mange tilfælde vil give mig flere poster med samme id, overskrift osv. Det sker fordi der kan være flere billeder tilknyttet samme post og det er netop den problemstilling jeg ikke kan løse.
Jeg skal groft sagt bruge poster med distinct id og som har mindst 1 billede tilknyttet.
Jeg har stadig ikke løst den, selvom jeg har prøvet forskellige joins og select-i-selects. Jeg mistænker man skal have gang i noget groupby men jeg kan ikke få mit hoved i gear til det.. :/
Ok. Men så: hvis post med id = 5 har 12 billeder tilknyttet, så vil du kun have id = 5 vist en gang. Men for hvilket af de 12 billeder vil du så have sti og filnavn? (Og du fortæller stadig ikke hvilket SQL system du bruger.)
Hvis du bare vil have sti og filnavn for det første billed i tabelen der er tilknyttet den pågældende post (og hvis du bruger mysql) så skulle dette virke:
SELECT p.id, overskrift, tekst, sti, filnavn FROM Poster p JOIN Billeder b ON p.id = b.post_id GROUP BY p.id ORDER BY p.id DESC LIMIT 3
Tak for dit forslag! :) Den giver dog: Column 'Poster.overskrift' is invalid in the select list because it is not contained in either an aggregate function or the GROUP BY clause
Det er i øvrigt MSSQL :)
Og jeg skal som skrevet bare bruge sti+filnavn på det første billede sorteret efter kolonnen prioritet i billedtabellen.
Jeg har egentlig fået den løst på en anden måde nu, men det virker ikke helt fint i kanten :)
Løsning:
with list as ( SELECT n.id, n.overskrift, n.dato, (SELECT TOP 1 (sti+filnavn) AS filsti FROM Billeder WHERE post_id = n.id AND sti is not NULL ORDER by prioritet ASC) AS filsti FROM Poster n ) select * from list where list.filsti is not null ORDER by dato DESC
SELECT TOP 3 P.id, P.overskrift, P.tekst, B.sti, B.filnavn FROM Billeder AS B INNER JOIN ( SELECT Billeder.post_id,Prioritet = MIN(Billeder.prioritet) FROM Billeder GROUP BY Billeder.post_id ) AS F ON (F.post_id = B.post_id AND F.Prioritet = B.prioritet) INNER JOIN Poster AS P ON (P.id = B.post_id) ORDER BY P.id DESC
Jeg ved ikke hvordan din Billeder.Prioritet "vender", men det er bare at bruge MAX() i stedet for MIN()
Måske du skal lægge TOP 3 ind i en inderste SELECT for at få en bedre plan ved store mængder data, men jeg har ikke lige data til at på- eller afvise det:
SELECT P.id, P.overskrift, P.tekst, B.sti, B.filnavn FROM Billeder AS B INNER JOIN ( SELECT TOP 3 Billeder.post_id,Prioritet = MIN(Billeder.prioritet) FROM Billeder GROUP BY Billeder.post_id ORDER BY post_id ) AS F ON (F.post_id = B.post_id AND F.Prioritet = B.prioritet) INNER JOIN Poster AS P ON (P.id = B.post_id) ORDER BY P.id DESC
Tak broholm og Christian_belgien for Jeres gode svar :) Det løste i hvert fald opgaven, men det viser sig at følgende er hurtigst execution:
with list as ( SELECT TOP 3 n.id, n.overskrift, n.dato, (SELECT TOP 1 (sti+filnavn) AS filsti FROM Billeder WHERE post_id = n.id AND sti is not NULL ORDER by prioritet ASC) AS filsti FROM Poster n ) select * from list where list.filsti is not null ORDER by dato DESC
Endnu engang tak for hjælpen! Håber det kan hjælpe andre også.
Jeg får ikke samme resultat på din forespørgsel, så det er svært at sammenligne dem. Spørgsmålet er hvilken der er korrekt? :-)
Synes godt om
Ny brugerNybegynder
Din løsning...
Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.