» »

MySQL Query Vprašanje

MySQL Query Vprašanje

KernelPanic ::

Spoštovani!

Imam tri tabele v Mysql Bazi:

Tabela A:
Id
Naziv

Tabela B
Id
Naziv

Tabela C
Id_A
Id_B

To je many to many relation. Kako zdej ven dobim iz tabele C podatke za record A.Id=1?? Karkol nardim, mi ne dela pravilno!

keworkian ::

Neki takega

SELECT c.* FROM table c
JOIN table a ON c.id_a = a.id
JOIN table b ON c.id_b = b.id
WHERE a.id = 1
Obscenities in B-Flat

KernelPanic ::

hmm zakwa pa join pr iskanju podatkov??

keworkian ::

Ups narobe prebral, my bad
select c.* from table c WHERE c.id_a IN (SELECT id FROM table a WHERE id = 1)
Obscenities in B-Flat

overlord_tm ::

keworkian je izjavil:

Ups narobe prebral, my bad
select c.* from table c WHERE c.id_a IN (SELECT id FROM table a WHERE id = 1)


Tole je pomoje enako kot:
SELECT * FROM C WHERE C.id_A = 1

ker SELECT id FROM table a WHERE id = 1 bo vedno vrnil ena. Lahko tudi vec enk ali pa prazno mnozico.

Ce rabis dobiti iz C tabele podatke za A.id = 1 samo en preprost select nad C-jem izvedes, kjer mora biti FK za tabelo A enak 1. Torej to zgoraj. Zakaj bi si pa zelel to, pa nevem. Glede na podane sheme dokaj nesmiselno.

keworkian ::

Tako čudne tabele ima, da me je rahlo zmedlo. soz.
Obscenities in B-Flat

KernelPanic ::

lol, kako cudne???

overlord_tm je izjavil:

keworkian je izjavil:

Ups narobe prebral, my bad
select c.* from table c WHERE c.id_a IN (SELECT id FROM table a WHERE id = 1)


Tole je pomoje enako kot:
SELECT * FROM C WHERE C.id_A = 1

ker SELECT id FROM table a WHERE id = 1 bo vedno vrnil ena. Lahko tudi vec enk ali pa prazno mnozico.

Ce rabis dobiti iz C tabele podatke za A.id = 1 samo en preprost select nad C-jem izvedes, kjer mora biti FK za tabelo A enak 1. Torej to zgoraj. Zakaj bi si pa zelel to, pa nevem. Glede na podane sheme dokaj nesmiselno.


Glej, imam tri realne tabele:
bwResorts:
Id
Name

bwFacilities:
Id
Name

ter
rlResortsHaveFacilities
IdResort
IdFacility

Torej, rad bi naredil poizvedbo, katere Facilites ima Resort z izbranim Id. Kako to naredim?

Zgodovina sprememb…

Tody ::

many to many se dela zveznimi tabelami in tujimi ključi.

KernelPanic ::

Ja pa sj to imam vse v bazi jao!!!! A morm celo tablo izdat?

KernelPanic ::

Torej, prisel sem do naslednjega stavka:
SELECT weblife.bwResorts.Id, weblife.bwResorts.Name
FROM weblife.bwResorts JOIN weblife.rlResortsHaveFacilities USING (weblife.rlResortsHaveFacilities.IdResort)
                       JOIN weblife.bwFacilities USING (weblife.rlResortsHaveFacilities.IdFacility)
ORDER BY weblife.bwFacilities.Id;


Pika v drugi vrstici v komandi USING (weblife.rlResortsHaveFacilities.IdResort) je vzrok za napako:
Error Code: 1064
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '.' at line 2
Mi lahko kdo pomaga, kaj tocno je narobe, ker mi ta napaka nikakor ni jasna.

Zgodovina sprememb…

overlord_tm ::

SELECT f.* FROM bwFacilities f WHERE f.Id IN
(SELECT rhf.IdFacility FROM rlResortsHaveFacilities rhf
WHERE rhf.IdResort = @tvojId)

ali
SELECT f.* FROM bwFacilities f
JOIN rlResortsHaveFacilities rhf ON f.Id = rhf.IdFacility
WHERE rhf.IdResort = @tvojId

ali
SELECT f.* FROM bwFacilities f 
JOIN rlResortsHaveFacilities rhf ON f.Id = rhf.IdFacility
JOIN bwResorts r ON r.Id = rhf.IdResort
WHERE rhf.IdResort = @tvojId


Prvi je nested querry, drugi je z joinom, tretji je tudi z joinom in malo nepotrebnim joinom (razen ce bos hkrati potreboval tudi podatke iz relacije resorts. Torej preizkusi prva dva querrya, drugi je bolj univerzalen, saj ga lahko uporabis tudi za kake druge namene. Hkrati pa iz tretjega lahko naredis view, kar bo programerjem olajsalo delo.

USING pa ne dela ker AFAIK je misljen kot nek poseben primer natural joina, za natural join je pa pogoj da imajo stolpci, po katerih se joina enako ime v shemah obeh relacij.

The USING(column_list) clause names a list of columns that must exist in both tables. If tables a and b both contain columns c1, c2, and c3, the following join compares corresponding columns from the two tables:


PS: Resno zacni uporabljat aliase ;) Pa lahko si malo bolj vljuden, saj ti isces pomoc. Ni ti treba cele tabele izdati, samo smiselen primer potrebujemo. Ampak tudi ce izdas, nebi smela biti kriza, v kolikor bo aplikacija kvalitetno narejena :) Ta zadnji query, ki si ga nalimal je narobe, napisal si za zelis videti katere facilitiese ima resort z izbranim id-jem, query pa izbere resorte, ki imajo dolocen facility. Sicer pa je tole one to many referenca pomoje, ker en facility lahko pripada samo enemu resortu, resort pa ima lahko vec faicilityev verjetno.

KernelPanic ::

overlord_tm je izjavil:

SELECT f.* FROM bwFacilities f WHERE f.Id IN
(SELECT rhf.IdFacility FROM rlResortsHaveFacilities rhf
WHERE rhf.IdResort = @tvojId)

ali
SELECT f.* FROM bwFacilities f
JOIN rlResortsHaveFacilities rhf ON f.Id = rhf.IdFacility
WHERE rhf.IdResort = @tvojId

ali
SELECT f.* FROM bwFacilities f 
JOIN rlResortsHaveFacilities rhf ON f.Id = rhf.IdFacility
JOIN bwResorts r ON r.Id = rhf.IdResort
WHERE rhf.IdResort = @tvojId


Prvi je nested querry, drugi je z joinom, tretji je tudi z joinom in malo nepotrebnim joinom (razen ce bos hkrati potreboval tudi podatke iz relacije resorts. Torej preizkusi prva dva querrya, drugi je bolj univerzalen, saj ga lahko uporabis tudi za kake druge namene. Hkrati pa iz tretjega lahko naredis view, kar bo programerjem olajsalo delo.

USING pa ne dela ker AFAIK je misljen kot nek poseben primer natural joina, za natural join je pa pogoj da imajo stolpci, po katerih se joina enako ime v shemah obeh relacij.

The USING(column_list) clause names a list of columns that must exist in both tables. If tables a and b both contain columns c1, c2, and c3, the following join compares corresponding columns from the two tables:


PS: Resno zacni uporabljat aliase ;) Pa lahko si malo bolj vljuden, saj ti isces pomoc. Ni ti treba cele tabele izdati, samo smiselen primer potrebujemo. Ampak tudi ce izdas, nebi smela biti kriza, v kolikor bo aplikacija kvalitetno narejena :) Ta zadnji query, ki si ga nalimal je narobe, napisal si za zelis videti katere facilitiese ima resort z izbranim id-jem, query pa izbere resorte, ki imajo dolocen facility. Sicer pa je tole one to many referenca pomoje, ker en facility lahko pripada samo enemu resortu, resort pa ima lahko vec faicilityev verjetno.
Hvala za razlago, vse lepo in prav, bom tudi bolj vljuden, vendar en facility je lahko pod vec resorti in en resort ima lahko vec resortov, tako, da je to many to many relacija!

S spo[tovanjenm,
Marko

KernelPanic ::

No to dela super, hvala, samo se nekaj. Sedaj me pa zajeba... PHP: kako podam parameter z PHP kodi za SQL stavek. Sledeca koda mi nikakor noce delati:
    while($rowResorts=mysql_fetch_row($resultResorts))
    {
        echo $rowResorts[0]." ".$rowResorts[1]." (RESORT)\n";	// displays resorts

        $numberOfResorts++;	// increase number of resorts

        $numberOfFacilities=0;    // inits facilities counter

        $resultResortFacilities=mysql_query('SELECT f.Id, f.Name,
                                             f.Address
                                             FROM weblife.bwFacilities f
                                             JOIN weblife.rlResortsHaveFacilities rhf ON f.Id=rhf.IdFacility
                                             JOIN weblife.bwResorts r ON r.Id=rhf.IdResort
                                             WHERE rhf.IdResort=%s',$rowResorts[0])
                                or die('Could not execute Resort Facilties Query ['.mysql_error().']');
        while($rowResortFacilities=mysql_fetch_row($resultResortFacilities))
        {
            echo "  ".$rowResortFacilities[0]." ".$rowResortFacilities[1]." ".$rowResortFacilities[2]."\n";

            $numberOfFacilities++;    // increase facilities counter
        }   // while - resort facilities inner loop

        if($numberOfFacilities==0)
        {
            echo " WARNING [There are no Facilites linked to Resort. Resort should be flagged as NON USED and ignored in final XML document]\n";
        }   // if
    }   // while - resort loop
Kako podam parameter v $resultResortFacilities query-ju?

S spostovanjem,
Marko

overlord_tm ::

 $resultResortFacilities = mysql_query(sprintf("SELECT f.Id, f.Name,
                                         f.Address
                                         FROM weblife.bwFacilities f
                                         JOIN weblife.rlResortsHaveFacilities rhf ON f.Id=rhf.IdFacility
                                         JOIN weblife.bwResorts r ON r.Id=rhf.IdResort
                                         WHERE rhf.IdResort = '%s'",mysql_real_escape_string($rowResorts[0])))
                            or die('Could not execute Resort Facilties Query ['.mysql_error().']');


Sicer pa bolj priporocam kak DB abstraction layer, recimo PDO.

Tist mysql_real_escape_string ni nujen, v kolikor popolnoma zaupas podatkom iz baze :) Ampak od prevec previdnosti glava ne boli. Pazi na SQL injection in XSS ;)

Zgodovina sprememb…

KernelPanic ::

overlord_tm je izjavil:

 $resultResortFacilities = mysql_query(sprintf("SELECT f.Id, f.Name,
f.Address
FROM weblife.bwFacilities f
JOIN weblife.rlResortsHaveFacilities rhf ON f.Id=rhf.IdFacility
JOIN weblife.bwResorts r ON r.Id=rhf.IdResort
WHERE rhf.IdResort = '%s'",mysql_real_escape_string($rowResorts[0])))
or die('Could not execute Resort Facilties Query ['.mysql_error().']');


Sicer pa bolj priporocam kak DB abstraction layer, recimo PDO.

Tist mysql_real_escape_string ni nujen, v kolikor popolnoma zaupas podatkom iz baze :) Ampak od prevec previdnosti glava ne boli. Pazi na SQL injection in XSS ;)
Zahvaljujem se ti za pomoc, vendar to ne deluje, vrne mi napako:
PHP Warning: mysql_query() expects parameter 2 to be resource, string given in /var/www/php_scripts/wl_get_all_merchandise.php on line 33

overlord_tm ::

$q = sprintf("SELECT f.Id, f.Name, f.Address
                                        FROM weblife.bwFacilities f
                                        JOIN weblife.rlResortsHaveFacilities rhf ON f.Id=rhf.IdFacility
                                        JOIN weblife.bwResorts r ON r.Id=rhf.IdResort
                                        WHERE rhf.IdResort = %s", mysql_real_escape_string($rowResorts[0]));
$resultResortFacilities = mysql_query($q) or die('Could not execute Resort Facilties Query ['.mysql_error().']');


Slisi se kot problem z oklepaji. Lahko naredis en echo $q spremenljivke, da vidis kak querry poslje. Problem je, ker mysql_querry komanda ima opcijsko drugi argument resource id (vrednost, ki jo shranis v spremenljivko, ko klices mysql_connect()). In ce so oklepaji nepravilno postavljeni je mozno, da se je kot drugi argument pojavil kak string.

Lahko pa probas tudi najbolj preporosto varianto:
$q = sprintf("SELECT f.Id, f.Name, f.Address
                                        FROM weblife.bwFacilities f
                                        JOIN weblife.rlResortsHaveFacilities rhf ON f.Id=rhf.IdFacility
                                        JOIN weblife.bwResorts r ON r.Id=rhf.IdResort
                                        WHERE rhf.IdResort = $rowResorts[0]");
$resultResortFacilities = mysql_query($q) or die('Could not execute Resort Facilties Query ['.mysql_error().']');


Spremenljivke v dvojnih okklepajih se razsirijo v svojo vrednost, vsaj ponavadi je tako :) Se vedno lahko naredis echo $q, da se preveri kak query se posilja.


Vredno ogleda ...

TemaSporočilaOglediZadnje sporočilo
TemaSporočilaOglediZadnje sporočilo
»

SQL vprasanje (strani: 1 2 )

Oddelek: Programiranje
687891 (4570) BivšiUser2
»

[SQL] Unikatni izpisi

Oddelek: Programiranje
212063 (1450) 111111111111
»

Normalizirana struktura - query

Oddelek: Programiranje
191640 (1260) frudi
»

MySQL vprašanje - redundanca recordov

Oddelek: Izdelava spletišč
8591 (526) KernelPanic
»

SQL problem

Oddelek: Programiranje
91453 (1290) Bossek

Več podobnih tem