Förberedelser inför SQL-intervjun · Lektion

Korrelerade EXISTS och NOT EXISTS

Det robusta anti-join-alternativet som hanterar NULL korrekt

Lektion 3 av 413 steg

Korrelerade EXISTS och NOT EXISTS är en gratis lektion i Förberedelser inför SQL-intervjun på CoddyKit. Detta är lektion 3 av 4. Ni kan läsa hela lektionen gratis nedan och sedan öva praktiskt i webbläsaren med en inbyggd kodredigerare och en AI-handledare som är tillgänglig dygnet runt. Den ingår i lärvägen för Förberedelser inför SQL-intervjun, och Era framsteg synkroniseras mellan webben och CoddyKit-appen. Kursen i Förberedelser inför SQL-intervjun innehåller totalt 4 lektioner.

EXISTS testar om något finns

EXISTS tar en underfråga och returnerar TRUE så snart underfrågan ger minst en rad, annars FALSE. Den returnerar aldrig själva raderna.

Med en korrelerad underfråga inuti blir EXISTS ett närvarotest för varje yttre rad: "finns det en matchande rad för den här yttre raden?"

Eftersom den avbryter vid den första träffen spelar det ingen roll hur många rader som matchar. Den här semantiska detaljen är en populär intervjupunkt.

Ett grundläggande korrelerat EXISTS

Hitta kunder som har lagt minst en order. Den inre frågan korreleras via o.customer_id = c.customer_id.

För varje kund frågar EXISTS: finns det någon order för den här kunden? Om svaret är ja behåller ni kunden.

SELECT c.customer_id, c.name
FROM customers c
WHERE EXISTS (
    SELECT 1
    FROM orders o
    WHERE o.customer_id = c.customer_id
);

Varför SELECT 1 används i EXISTS

Ni kommer att se SELECT 1, SELECT * eller SELECT NULL inuti EXISTS. De är likvärdiga.

EXISTS kontrollerar bara om några rader returneras, aldrig deras innehåll, så de projicerade kolumnerna saknar betydelse. Optimeraren ignorerar dem.

SELECT 1 är en vanlig konvention som signalerar avsikten: "Jag bryr mig bara om huruvida något finns." Välj en variant och var konsekvent; låt inte intervjuaren tro att kolumnlistan har betydelse här.

NOT EXISTS hittar det som saknas

NOT EXISTS vänder på testet: behåll den yttre raden endast när den korrelerade underfrågan returnerar inga rader.

Det här är det klassiska anti-join-mönstret: kunder utan order, produkter som aldrig har sålts och studenter utan inlämningar.

SELECT c.customer_id, c.name
FROM customers c
WHERE NOT EXISTS (
    SELECT 1
    FROM orders o
    WHERE o.customer_id = c.customer_id
);

NULL-fällan i NOT IN

Här kommer den viktiga intervjupunkten. NOT IN mot en underfråga som kan innehålla NULL beter sig förrädiskt: om listan innehåller ens ett NULL returnerar NOT IN inga rader alls.

Det beror på att en jämförelse med NULL ger UNKNOWN och att NOT IN kräver att varje jämförelse ska vara falsk. Ett enda UNKNOWN förgiftar hela villkoret.

NOT EXISTS drabbas inte av detta. Den kontrollerar helt enkelt om en rad finns och hanterar NULL på ett säkert sätt.

-- Risky: returns nothing if any o.customer_id is NULL
SELECT c.customer_id FROM customers c
WHERE c.customer_id NOT IN (SELECT o.customer_id FROM orders o);

-- Safe: NULLs do not break it
SELECT c.customer_id FROM customers c
WHERE NOT EXISTS (
    SELECT 1 FROM orders o WHERE o.customer_id = c.customer_id
);

Varför NOT EXISTS är NULL-säkert

Förklaringen finns i matchningslogiken. NOT EXISTS kontrollerar om någon inre rad uppfyller o.customer_id = c.customer_id.

En rad där o.customer_id är NULL uppfyller aldrig den likheten (NULL = vad som helst ger UNKNOWN, inte TRUE), så den räknas helt enkelt inte som en matchning. Närvarotestet förblir korrekt.

Med NOT IN blir samma NULL i stället en del av en listjämförelse vars UNKNOWN-resultat slår ut hela resultatet. Därför föredrar seniora intervjuare NOT EXISTS.

EXISTS med extra villkor

Den korrelerade underfrågan kan innehålla fler predikat. Hitta kunder som har lagt minst en order på över 1000.

Det extra villkoret finns inuti EXISTS-underfrågan och avgränsas per kund.

SELECT c.customer_id, c.name
FROM customers c
WHERE EXISTS (
    SELECT 1
    FROM orders o
    WHERE o.customer_id = c.customer_id
      AND o.amount > 1000
);

Prestanda: kortslutningsbeteende

EXISTS kan sluta skanna den inre relationen så snart en matchande rad hittas. Den bygger inte upp eller räknar en fullständig resultatmängd.

Det gör vanligtvis EXISTS effektivt, särskilt när den korrelerade kolumnen är indexerad, eftersom varje sökning per rad snabbt kan hitta en match och avslutas.

Jämför med en korrelerad COUNT(*) > 0, som tvingar databasen att räkna alla matchningar. Föredra EXISTS när du bara behöver ett ja- eller nej-svar.

EXISTS kontra COUNT för att kontrollera förekomst

Ibland skriver kandidater en korrelerad räkning för att kontrollera om något förekommer. Det fungerar, men innebär onödigt arbete.

COUNT-versionen räknar alla matchande order, medan EXISTS avslutar efter den första. För ett rent förekomsttest uttrycker EXISTS avsikten tydligt och låter optimeraren kortsluta.

-- Works but counts everything
SELECT c.customer_id FROM customers c
WHERE (SELECT COUNT(*) FROM orders o
       WHERE o.customer_id = c.customer_id) > 0;

-- Better: stops at first match
SELECT c.customer_id FROM customers c
WHERE EXISTS (SELECT 1 FROM orders o
              WHERE o.customer_id = c.customer_id);

Genomarbetat exempel: produkter som aldrig har beställts

En klassisk intervjufråga om anti-join: lista produkter som aldrig har beställts. NOT EXISTS ligger nästan lika nära som det engelska kravet.

Kontrollera för varje produkt om någon orderrad refererar till den och behåll bara de produkter som saknar sådana rader.

SELECT p.product_id, p.name
FROM products p
WHERE NOT EXISTS (
    SELECT 1
    FROM order_items oi
    WHERE oi.product_id = p.product_id
);

EXISTS i NOT EXISTS för frågor av divisionstyp

Att kapsla EXISTS i NOT EXISTS uttrycker relationsdivision: "hitta rader som matchar ALLA element i en mängd." En klassisk uppgift är "kunder som har beställt alla produkter i en kategori."

Logiken är: behåll en kund när det inte finns någon produkt som kunden inte har beställt. Den dubbla negationen är kännetecknande för en divisionsfråga, och intervjuare använder den för att testa djupa kunskaper om EXISTS.

SELECT c.customer_id
FROM customers c
WHERE NOT EXISTS (
    SELECT 1 FROM products p
    WHERE p.category = 'Coffee'
      AND NOT EXISTS (
          SELECT 1 FROM order_items oi
          JOIN orders o ON o.order_id = oi.order_id
          WHERE oi.product_id = p.product_id
            AND o.customer_id = c.customer_id
      )
);

Snabbkontroll

Välj det säkraste sättet att hitta kunder utan order.

Sammanfattning: korrelerade EXISTS och NOT EXISTS

Viktiga lärdomar:

  • EXISTS är ett förekomsttest per rad som kortsluter vid den första matchningen. Vilken kolumn som väljs inuti saknar betydelse (använd SELECT 1).
  • NOT EXISTS är en NULL-säker anti-join för att hitta rader utan matchning.
  • NOT IN med en NULL i listan returnerar ingenting. Föredra NOT EXISTS.
  • För förekomst är EXISTS bättre än en korrelerad COUNT(*) > 0, eftersom den avslutar tidigt.

Nämn NOT IN-fällan med NULL utan att bli tillfrågad. Det är ett pålitligt tecken på SQL-mognad.

Gratis att börja

Lär dig SQL med en AI-lärare – gratis

Skriv och kör riktig kod i webbläsaren, få omedelbar hjälp av en AI-lärare dygnet runt och fortsätt där du slutade – på webben eller i appen.

Kurser
30
Lektioner
120

Vanliga frågor

Är lektionen ”Korrelerade EXISTS och NOT EXISTS” gratis?

Ja – hela texten till ”Korrelerade EXISTS och NOT EXISTS” kan läsas gratis här på webben. Om Ni vill öva interaktivt med en inbyggd kodredigerare och en AI-handledare som är tillgänglig dygnet runt och låsa upp resten av kursen i Förberedelser inför SQL-intervjun, kan Ni uppgradera till CoddyKit PRO. Kursen i Förberedelser inför SQL-intervjun innehåller totalt 4 lektioner.

Vad lär jag mig i ”Korrelerade EXISTS och NOT EXISTS”?

Det robusta anti-join-alternativet som hanterar NULL korrekt Ni övar på Förberedelser inför SQL-intervjun med praktisk kod som körs direkt i webbläsaren, medan en AI-handledare som är tillgänglig dygnet runt svarar på Era frågor under lektionen.

Behöver jag någon erfarenhet för att börja lära mig Förberedelser inför SQL-intervjun?

Du behöver inga förkunskaper. Utbildningen i Förberedelser inför SQL-intervjun på CoddyKit är upplagd för allt från nybörjare till avancerade elever, så att du kan börja här eller från början och gå fram i din egen takt. Detta är lektion 3 av 4.

Hur lång tid tar lektionen ”Korrelerade EXISTS och NOT EXISTS”?

De flesta CoddyKit-lektioner tar cirka 5–10 minuter. Varje lektion är kort och interaktiv, så att du gör stadiga framsteg och kan fortsätta precis där du slutade – på webben eller i appen.

Kan jag skriva och köra kod i den här Förberedelser inför SQL-intervjun-lektionen?

Ja. Varje Förberedelser inför SQL-intervjun-lektion innehåller en inbyggd kodredigerare, så att du kan skriva och köra riktig kod direkt i webbläsaren och få omedelbar AI-feedback – utan lokal installation.

Alla lektioner i den här kursen

  1. En korrelerad underfrågas anatomi
  2. Aggregeringar per grupp utan GROUP BY
  3. Korrelerade EXISTS och NOT EXISTS
  4. Skriv om korrelerade underfrågor som joinar
← Tillbaka till Förberedelser inför SQL-intervjun