[MySQL] SQL join doormiddel van reference-tabel

Pagina: 1
Acties:

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ik heb een 2-tal tabellen waar wat informatie in staat, de een is een "gebruiker-tabel" de andere is een "verenigingen-tabel" (voorbeeld).

Het kan zijn dat een gebruiker lid is van meedere verenigingen, dus wil ik hiervoor een reference table gebruiken om meerdere combinaties te maken:


code:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
gebruikers
-------------------------------------
id  |    name    |     city    |
-------------------------------------
1  |    jan        |     amst   |
2  |    piet       |     utr      |
3  |    klaas    |      arnh   |
-------------------------------------

verenigingen
-------------------------------------
id  |    name    |     city    |
-------------------------------------
1  |    ver1       |     amst  |
2  |    ver2       |     utr      |
3  |    ver3       |     arnh   |
-------------------------------------

user_ver
-------------------------------------
id  |    userid    |     verid  |
-------------------------------------
1  |    3           |       2     |
2  |    1           |      3      |
3  |    3           |      1      |
-------------------------------------


Zoals jullie zien is klaas lid van meedere verenigingen. Stel ik wil de plaatsen van de verenigingen van Klaas opvragen dan moet ik gebruik maken van de reference tabel.

Het lijkt met dat ik een join moet doen en daarna een rightjoin. Ik heb wel een voorbeeld query welke ik weer even op orde moet brengen omdat ik er niet uit kwam, vandaar dit topic dus.

Een reference tabel lijkt me het makkelijkste toch ?

[ Voor 3% gewijzigd door Verwijderd op 03-01-2009 01:31 ]


Acties:
  • 0 Henk 'm!

  • NMe
  • Registratie: Februari 2004
  • Laatst online: 09-09 13:58

NMe

Quia Ego Sic Dico.

SQL:
1
2
3
SELECT ..
FROM `gebruikers` LEFT JOIN `users_ver` ON ...
                  INNER JOIN `verenigingen` ON ...

Dat gaat ervanuit dat je gebruikers kan hebben die niet in een vereniging zitten; als die niet bestaan zijn twee inner joins afdoende.

'E's fighting in there!' he stuttered, grabbing the captain's arm.
'All by himself?' said the captain.
'No, with everyone!' shouted Nobby, hopping from one foot to the other.


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
NMe schreef op zaterdag 03 januari 2009 @ 01:37:
SQL:
1
2
3
SELECT ..
FROM `gebruikers` LEFT JOIN `users_ver` ON ...
                  INNER JOIN `verenigingen` ON ...

Dat gaat ervanuit dat je gebruikers kan hebben die niet in een vereniging zitten; als die niet bestaan zijn twee inner joins afdoende.
In dat geval draai je dus de query om in plaats van hetgeen wat ik er mee wil doen ?

Soortement van "negatief" dus.


Werkt prima, toch mag je als je wil even aanvullen wat je bedoelde met je commentaar :)

[ Voor 12% gewijzigd door Verwijderd op 03-01-2009 02:02 ]


Acties:
  • 0 Henk 'm!

  • farlane
  • Registratie: Maart 2000
  • Laatst online: 15-09 17:16
Verwijderd schreef op zaterdag 03 januari 2009 @ 01:43:
Werkt prima, toch mag je als je wil even aanvullen wat je bedoelde met je commentaar :)
Een inner join selecteert alleen records als ze in beide tabellen van de join staan, dus je krijgt alleen personen die in een vereniging zitten en niet de personen die niet in een vereniging zitten ( want deze hebben geen record in de koppeltabel )

Somniferous whisperings of scarlet fields. Sleep calling me and in my dreams i wander. My reality is abandoned (I traverse afar). Not a care if I never everwake.


Acties:
  • 0 Henk 'm!

  • Enfer
  • Registratie: Februari 2004
  • Laatst online: 18:57
En nog een aanvulling:
De LEFT JOIN zorgt ervoor dat uit de linker tabel (eerste) die je joint, alle rijen sowiezo in je resultaat voorkomen, bij deze query dus gebruikers.
Als een gebruiker geen vereniging heeft, zal er dus NULL komen te staan in die betreffende kolom(men)

Acties:
  • 0 Henk 'm!

  • NMe
  • Registratie: Februari 2004
  • Laatst online: 09-09 13:58

NMe

Quia Ego Sic Dico.

En om het verhaaltje compleet te maken: MySQL kan (kon?) niet goed met indexen werken zolang je een right join gebruikt, wat de reden is dat ik jou idee "omgedraaid" heb naar een left join. ;)

'E's fighting in there!' he stuttered, grabbing the captain's arm.
'All by himself?' said the captain.
'No, with everyone!' shouted Nobby, hopping from one foot to the other.


Acties:
  • 0 Henk 'm!

  • pimlie
  • Registratie: November 2000
  • Laatst online: 11:20
NMe schreef op zaterdag 03 januari 2009 @ 12:37:
En om het verhaaltje compleet te maken: MySQL kan (kon?) niet goed met indexen werken zolang je een right join gebruikt, wat de reden is dat ik jou idee "omgedraaid" heb naar een left join. ;)
Maar in dit geval moet je wel een nested join aanmaken. Anders maakt mysql van de eerste left ook een inner en krijg je dus minder resultaten terug dan verwacht ;)

Bedoel dus dit:
SQL:
1
2
3
4
SELECT .. 
FROM `gebruikers` LEFT JOIN (`users_ver` 
                  INNER JOIN `verenigingen` ON ...
) ON ... 

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
pimlie schreef op zaterdag 03 januari 2009 @ 12:48:
[...]


Maar in dit geval moet je wel een nested join aanmaken. Anders maakt mysql van de eerste left ook een inner en krijg je dus minder resultaten terug dan verwacht ;)

Bedoel dus dit:
SQL:
1
2
3
4
SELECT .. 
FROM `gebruikers` LEFT JOIN (`users_ver` 
                  INNER JOIN `verenigingen` ON ...
) ON ... 
Dit werkt opzich prima, ik gebruik het zonder problemen om formfields te vullen.

Ik kom er net achter dat als ik een select hiermee vul waar er maar 1 record in een tabel beschikbaar is, komt deze er toch 3x in te staan... een of andere rare loop.

Acties:
  • 0 Henk 'm!

  • StephanVierkant
  • Registratie: Mei 2003
  • Laatst online: 08-09 16:22
GROUP BY :)

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Ik heb er vanacht echt onwijs lang mee zitten rommelen en gelezen wat er nu mis gaat.

Het blijkt dat mijn Join niet goed is, wat ik namelijk doe is dit:


code:
1
2
 SELECT * FROM `gebruikers` LEFT JOIN `user_ver` ON  user_ver.userid =" . $db->qstr
                     ( $_SESSION['user_id'] ) . " INNER JOIN `verenigingen` ON verenigingen.id=user_ver.verid"


Aangezien ik 3 leden in mijn gebruikerstabel heb staan en de sessie-variabele als variabele in mij query gebruik gaat het niet goed. Als ik in plaats van die sessievariabele gewoon "gebruikers.id" invul gaat het beter natuurlijk.

Ik wil alleen bepalen voor welke gebuiker hij het laat zien.

Je kunt ook 2 while loops in elkaar gebuiker, maar een join query lijkt me netter.

Mijn doel is dus om allee verenigenen voor een bepaalde gebruiker te laten zien.

[ Voor 4% gewijzigd door Verwijderd op 06-01-2009 13:59 ]


Acties:
  • 0 Henk 'm!

  • StephanVierkant
  • Registratie: Mei 2003
  • Laatst online: 08-09 16:22
Beperk je eerste instantie even alleen tot SQL, als je gaat testen in phpMyAdmin weet je zeker dat je geen PHP-fouten maakt. Da's wat beter debuggen lijkt me.

Wat wil je precies hebben? Als ik altijd goed (in normaal Nederlands) formuleer welke gegevens ik wil hebben, helpt het mij persoonlijk ook altijd al in m'n zoektocht naar de oplossing (en als je het ook aan ons vertelt, kunnen we je ook helpen ;))

WHERE verenigingen.id = '1' al geprobeerd trouwens? :)

[ Voor 6% gewijzigd door StephanVierkant op 06-01-2009 18:25 ]


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Stephan4kant schreef op dinsdag 06 januari 2009 @ 18:14:
Beperk je eerste instantie even alleen tot SQL, als je gaat testen in phpMyAdmin weet je zeker dat je geen PHP-fouten maakt. Da's wat beter debuggen lijkt me.
Was ik intussen al aan het doen, dit werkt vaak makkelijker inderdaad.
Wat wil je precies hebben? Als ik altijd goed (in normaal Nederlands) formuleer welke gegevens ik wil hebben, helpt het mij persoonlijk ook altijd al in m'n zoektocht naar de oplossing (en als je het ook aan ons vertelt, kunnen we je ook helpen ;))

WHERE verenigingen.id = '1' al geprobeerd trouwens? :)
Ik wil dus weergeven aan de hand van het id van de user van welke verenigingen hij lid is.

Ik heb de userid in een sessie staan, jouw where zal dus waarschijnlijk niet werken.

Acties:
  • 0 Henk 'm!

  • SeeniX
  • Registratie: Maart 2002
  • Laatst online: 18-10-2009
Verwijderd schreef op dinsdag 06 januari 2009 @ 19:13:
Ik heb de userid in een sessie staan, jouw where zal dus waarschijnlijk niet werken.
dan moet je 'm veranderen in

code:
1
2
SELECT * FROM `gebruikers` LEFT JOIN `user_ver` ON  user_ver.userid = gebruikers.userid INNER JOIN `verenigingen` ON verenigingen.id=user_ver.verid WHERE gebruikers.userid=" . $db->qstr
                     ( $_SESSION['user_id'] ) . "

d-Media || web development & more;


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Oud topic dat ik even omhoog moet schoppen omdat ik ergens achter kwam.

Als ik deze query ombouw naar ZF naar krijg ik veel records terug omdat alles uit gebruikers, verenigingen en user_ver wordt gehaald.

Als ik de query gebruik zoals hij hierin staat native onder mysql_ dan krijg ik gewoon maar de records van de verenigingen terug waar een user toe behoort.

Hoe kan dit zo komen ?

Acties:
  • 0 Henk 'm!

  • Creepy
  • Registratie: Juni 2001
  • Laatst online: 19:20

Creepy

Tactical Espionage Splatterer

Een query is een query, dus dat zou geen verschil moeten maken. Dus hoe voer je de query precies uit en weet je 100% zeker dat de juiste query op de juiste manier wordt uitgevoerd? (aka: druk de query eens op je scherm af :P ).

"I had a problem, I solved it with regular expressions. Now I have two problems". That's shows a lack of appreciation for regular expressions: "I know have _star_ problems" --Kevlin Henney


Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Creepy schreef op maandag 11 mei 2009 @ 15:44:
Een query is een query, dus dat zou geen verschil moeten maken. Dus hoe voer je de query precies uit en weet je 100% zeker dat de juiste query op de juiste manier wordt uitgevoerd? (aka: druk de query eens op je scherm af :P ).
Ja de query heb ik afgedrukt en zou goed moeten zijn:

Komt ie !

code:
1
SELECT `users`.*, `user_comp`.*, `company`.* FROM `users` LEFT JOIN `user_comp` ON user_comp.user_id=users.id INNER JOIN `company` ON company.id=user_comp.comp_id WHERE (users.id = '3')


Bovenstaand is even een andere versie overigens :)

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
Opgelost !

Moest een fetchAll doen :)

Moet nog een beetje wennen maar dit gaat zo lekker !
Pagina: 1