Mga nested na query sa SQL
Binibigyang-daan ka ng wikang SQL na mag-nest ng isang query sa loob ng isa pang query. Ginagawa nitong posible na magsulat ng isang napakalaking query na gagawa ng isang bagay na malaki at kumplikado, kahit na ang pagiging madaling mabasa ng code ay lubhang nabawasan.
Depende sa kung gaano karaming mga halaga ang ibinalik ng mga subquery, ang lugar kung saan maaaring ilapat ang mga ito ay nagbabago. Mayroong tatlong mga opsyon sa kabuuan:
- Ang subquery ay nagbabalik ng isang solong halaga (isang hanay at isang hilera).
- Ang subquery ay nagbabalik ng isang listahan ng mga halaga (isang talahanayan na may isang haligi).
- Ang subquery ay nagbabalik ng isang talahanayan (maraming mga hanay, anumang bilang ng mga hilera).
Tingnan natin ang isang halimbawa para sa bawat kaso.
Subquery na may scalar na resulta
Maghanap tayo ng listahan ng lahat ng ating mga empleyado mula sa talahanayan ng empleyado na ang suweldo ay mas mataas kaysa sa karaniwan para sa kumpanya. Paano natin ito magagawa?
Madali nating ma-filter ang mga empleyado sa pamamagitan ng paghahambing ng kanilang suweldo sa average kung alam natin ito nang maaga. Kasabay nito, nakapagsulat na kami ng query na nagbibigay-daan sa amin na kalkulahin ang average na suweldo ng mga empleyado ng kumpanya. Tandaan natin ito:
SELECT AVG(salary) FROM employee
Pagkatapos ay ibinalik sa amin ng MySQL ang halaga: 76833.3333 .
Paano ngayon makahanap ng isang listahan ng lahat ng mga empleyado na ang suweldo ay higit sa average? Ito rin ay napaka-simple:
SELECT * FROM employee
WHERE salary > 76833.3333
Ang magiging resulta ng query na ito ay:
id | pangalan | hanapbuhay | suweldo |
---|---|---|---|
1 | Ivanov Ivan | Programmer | 100000 |
2 | Petrov Petr | Programmer | 80000 |
4 | Rabinovich Moisha | Direktor | 200000 |
At ngayon pinagsasama na lang namin ang parehong mga kahilingan sa pamamagitan ng pagpapalit sa unang kahilingan sa halip na ang halagang 76833:
SELECT * FROM employee
WHERE salary > (SELECT AVG(salary) FROM employee)
Magiging pareho ang resulta ng query na ito:
id | pangalan | hanapbuhay | suweldo |
---|---|---|---|
1 | Ivanov Ivan | Programmer | 100000 |
2 | Petrov Petr | Programmer | 80000 |
4 | Rabinovich Moisha | Direktor | 200000 |
Subquery na may listahan ng mga halaga
Naaalala mo ba noong unang panahon na mayroon tayong gawain - hanapin ang lahat ng mga talaan mula sa isang talahanayan kung saan walang katumbas na mga talaan mula sa iba?
Nagkaroon din ng ganitong larawan:
![](https://cdn.codegym.cc/images/article/a0eff64c-0bb4-4480-833e-c1305cd03a5e/512.jpeg)
Kung hindi ako nagkakamali, ang gawain ay ang mga sumusunod: magpakita ng listahan ng lahat ng empleyado mula sa talahanayan ng empleyado kung saan walang mga gawain sa talahanayan ng gawain .
Maghanap din tayo ng solusyon sa dalawang hakbang.
Una, magsulat tayo ng query na magbabalik ng id ng lahat ng empleyado na may mga gawain sa talahanayan ng gawain. Tandaan lamang ang dalawang bagay:
- alisin ang mga duplicate - gamitin ang DISTINCT na keyword.
- alisin ang mga halaga ng NULL mula sa resulta.
SELECT DISTINCT employee_id FROM task
WHERE employee_id IS NOT NULL
At dito nakakuha kami ng magandang resulta ng naturang kahilingan:
employee_id |
---|
1 |
2 |
5 |
4 |
6 |
Pansamantala nating isulat ito para sa kaginhawahan bilang isang sequence: 1,2,5,4,6. Ngayon magsulat tayo ng pangalawang query - sa talahanayan ng empleyado, na magbabalik ng isang listahan ng mga empleyado na ang id ay hindi nakapaloob sa unang listahan:
SELECT * FROM employee
WHERE id NOT IN (1,2,5,4,6)
At ang resulta ng query na ito:
id | pangalan | hanapbuhay | suweldo | edad | Sumali sa date |
---|---|---|---|---|---|
3 | Ivanov Sergey | Tester | 40000 | tatlumpu | 2014-01-01 |
At ngayon, tulad ng sa nakaraang halimbawa, maaari mong pagsamahin ang parehong mga kahilingan sa pamamagitan lamang ng pagpapalit sa katawan ng unang kahilingan sa halip na sa listahan ng id.
SELECT * FROM employee
WHERE id NOT IN (
SELECT DISTINCT employee_id FROM task
WHERE employee_id IS NOT NULL
)
GO TO FULL VERSION