En subforespørgsel er en forespørgsel indlejret i en anden forespørgsel — brugt i WHERE, FROM, SELECT eller med EXISTS. Det lader dig bruge resultatet af en forespørgsel inden i en anden, hvilket muliggør kompleks filtrering og beregninger.
En subforespørgsel er en forespørgsel indlejret i en anden forespørgsel — brugt i WHERE, FROM, SELECT eller med EXISTS. Det lader dig bruge resultatet af en forespørgsel inden i en anden, hvilket muliggør kompleks filtrering og beregninger.
-- find users who have placed an order (their id is in the orders table)
SELECT name FROM users
WHERE id IN (SELECT user_id FROM orders); -- the subquery returns a list of user_ids
-- find products more expensive than the average
SELECT name, price FROM products
WHERE price > (SELECT AVG(price) FROM products); -- subquery returns a single value
En subforespørgsel i WHERE leverer værdier til filtrering — en liste (med IN) eller en enkelt værdi (med sammenligningsoperatorer).
-- for each user, find those with above-average orders FOR THEIR COUNTRY
SELECT name FROM users u
WHERE order_count > (
SELECT AVG(order_count) FROM users
WHERE country = u.country -- references the OUTER query's row (correlated)
);
En korreleret subforespørgsel henviser til den ydre forespørgsel — den kører én gang pr. ydre række (potentielt langsommere). En ukorreleret subforespørgsel kører én gang.
-- users who have at least one order (often more efficient than IN)
SELECT name FROM users u
WHERE EXISTS (
SELECT 1 FROM orders o WHERE o.user_id = u.id -- just checks existence
);
EXISTS kontrollerer, om en subforespørgsel returnerer nogen rækker — ofte mere effektivt end IN for eksistenskontroller (den kan stoppe ved første match).
-- use a subquery result as a table
SELECT country, avg_age FROM (
SELECT country, AVG(age) AS avg_age FROM users GROUP BY country
) AS country_stats
WHERE avg_age > 30;
Many subqueries can be rewritten as JOINs (often more efficient/readable).
WHERE id IN (SELECT ...) → can often be a JOIN
Use subqueries for clarity in filtering/aggregation; JOINs for combining data.
CTEs (WITH) are often a cleaner alternative to complex nested subqueries.
Subforespørgsler er en vigtig SQL-teknik for kompleks forespørgsling — at bruge resultatet af en forespørgsel inden i en anden muliggør filtrering og beregninger, som simple forespørgsler ikke kan udtrykke, så forståelse af dem er værdifuld for at skrive forespørgsler i den virkelige verden.
At kende formerne — subforespørgsler i WHERE (filtrering efter en liste med IN eller en enkelt værdi med sammenligninger), korrelerede subforespørgsler (der henviser til den ydre forespørgsel, kørende pr. række), EXISTS (effektive eksistenskontroller) og subforespørgsler i FROM (afledte tabeller) — dækker de almindelige mønstre for at udtrykke kompleks logik.
At forstå skellet mellem korrelerede og ukorrelerede subforespørgsler er vigtig for ydeevne (korrelerede subforespørgsler kører én gang pr. ydre række og kan være langsomme).
Ligeledes værdifuldt er at kende forholdet til JOINs og CTEer: mange subforespørgsler kan omskrives som JOINs (ofte mere effektivt og læsbart) eller CTEer (renere for komplekse tilfælde), så forståelse af hvornår man skal bruge hver — subforespørgsler for filtrering/aggregeringklarhed, JOINs for at kombinere data — er en praktisk færdighed.
Da forespørgsler i den virkelige verden ofte kræver indlejring (filtrering efter aggregerede resultater, eksistenskontroller, sammenligning med beregnede værdier), og da forståelse af subforespørgsler, deres ydelsekarakteristika (især korrelerede), og deres forhold til JOINs/CTEer er vigtig for at skrive effektive, velordnede komplekse forespørgsler, er beherskelse af subforespørgsler værdifuld, hyppigt anvendt viden for SQL ud over grundlæggende forespørgsling og et almindeligt interviewemne, der viser evnen til at udtrykke komplekse datakrav.