Seq Scan jämfört med Index Scan och Index-Only
Förstå varför frågeplaneraren väljer varje alternativ och vad det säger om er fråga.
Seq Scan jämfört med Index Scan och Index-Only är en gratis lektion i Förberedelse inför kodningsintervjuer på CoddyKit. Detta är lektion 2 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örberedelse inför kodningsintervjuer, och Era framsteg synkroniseras mellan webben och CoddyKit-appen. Kursen i Förberedelse inför kodningsintervjuer innehåller totalt 4 lektioner.
Tre sätt att läsa en tabell
När planeraren behöver rader från en tabell väljer den en av tre åtkomstmetoder, och intervjuare förväntar sig att ni kan nämna alla tre:
- Seq Scan, läser varje rad i tabellen från början till slut.
- Index Scan, går igenom ett index för att hitta matchande rader och hämtar sedan var och en från tabellen.
- Index-Only Scan, besvarar frågan helt från indexet utan att röra tabellen över huvud taget.
Att förstå varför planeraren väljer respektive metod är kärnan i denna lektion och en given seniorfråga.
Vad en sekventiell genomsökning gör
En Seq Scan läser tabellens sidor efter varandra och tillämpar eventuella filter på varje rad. Inget index används.
Det låter dåligt, men är ofta det rätta valet. Sekventiella läsningar är snabba för disken (inga slumpmässiga hopp), så när en fråga returnerar en stor andel av tabellen är det effektivare att genomsöka allt än att hoppa genom ett index miljoner gånger.
Exemplet: genomsök orders och behåll rader där amount > 100. Om de flesta beställningar överstiger 100 är en seq scan rätt val.
EXPLAIN SELECT * FROM orders WHERE amount > 100;
Seq Scan on orders (cost=0.00..18334.00 rows=900000 width=64)
Filter: (amount > 100)Vad en indexgenomsökning gör
En Index Scan använder ett B-träd för att hoppa direkt till matchande nycklar och läser sedan motsvarande rader från tabellens heap.
Den är effektiv när filtret är selektivt och returnerar en liten del av tabellen. Att slå upp 5 rader via ett index är bättre än att läsa 10 miljoner.
Planen anger vilket index som användes. Varje träff kostar en indexuppslagning plus en hämtning från heapen (en slumpmässig läsning), så indexgenomsökningar förlorar sin fördel när de returnerar för många rader.
EXPLAIN SELECT * FROM orders WHERE customer_id = 42;
Index Scan using idx_orders_customer on orders
(cost=0.42..38.50 rows=12 width=64)
Index Cond: (customer_id = 42)Selektivitet avgör valet
Det centrala begreppet bakom allt detta är selektivitet: hur stor andel av raderna som ett predikat behåller.
- Hög selektivitet (få rader matchar, till exempel ett unikt id) gynnar en Index Scan.
- Låg selektivitet (många rader matchar, till exempel
status IS NOT NULL) gynnar en Seq Scan.
En vanlig tumregel är att planeraren ofta föredrar en sekventiell genomsökning när en fråga returnerar mer än ungefär 5 till 10 procent av en tabell, eftersom de slumpmässiga hämtningarna från heapen vid en indexgenomsökning då blir dyrare än att läsa allt i ordning.
Fällan med visibility map
En Index-Only Scan är snabbast av de tre. Om varje kolumn som frågan behöver redan finns i indexet behöver motorn aldrig röra tabellens heap.
Exempelfrågan väljer endast customer_id och filtrerar på den, och indexet är skapat på customer_id. Alla data som behövs finns i indexet, så Postgres rapporterar Index Only Scan.
Detta undviker de slumpmässiga hämtningarna från heapen som gör en vanlig indexgenomsökning långsammare, vilket är en stor fördel i breda tabeller.
EXPLAIN SELECT customer_id FROM orders WHERE customer_id = 42;
Index Only Scan using idx_orders_customer on orders
(cost=0.42..8.44 rows=12 width=4)
Index Cond: (customer_id = 42)Fallgropen med synlighetskartan
Intervjuare älskar den här nyansen. En index-only-genomsökning måste fortfarande bekräfta att varje rad är synlig för er transaktion (MVCC), och indexet lagrar inte synlighetsinformation.
Postgres använder visibility map: om en sida är markerad som all-visible hoppar motorn över heapen; annars måste den hämta heap-raden ändå. Planen visar Heap Fetches: N.
Det är därför en nyligen uppdaterad tabell kan visa många heap-hämtningar och långsamma index-only-genomsökningar tills VACUUM uppdaterar visibility map.
Index Only Scan using idx_orders_customer on orders
(actual time=0.01..0.03 rows=12 loops=1)
Heap Fetches: 0Bitmappsgenomsökningar: medelvägen
Det finns en fjärde metod som ofta visas: Bitmap Heap Scan. Planeraren väljer den när ett predikat matchar fler rader än vad en vanlig indexgenomsökning lämpar sig för, men färre än en hel tabell.
Först bygger den en bitmap över matchande radplatser från indexet (Bitmap Index Scan) och hämtar sedan heapsidor i fysisk ordning i stället för slumpmässig ordning. Ordnade hämtningar är mycket billigare än de utspridda läsningarna vid en vanlig indexgenomsökning.
Bitmap Heap Scan on orders (cost=12.0..520.0 rows=8000)
Recheck Cond: (status = 'pending')
-> Bitmap Index Scan on idx_orders_status
(cost=0..12 rows=8000)
Index Cond: (status = 'pending')Varför planeraren ignorerade ert index
En klassisk intervjufråga: Jag lade till ett index, men planen gör fortfarande en Seq Scan. Varför? Vanliga orsaker:
- Predikatet är inte selektivt; en genomsökning är faktiskt billigare.
- En funktion omsluter kolumnen:
WHERE lower(email) = ...kan inte använda ett vanligt index påemail. - Typmismatch tvingar fram en implicit typkonvertering som gör att indexet inte kan användas.
- Inaktuell statistik; kör
ANALYZE. - Tabellen är liten; att läsa några få sidor är billigare än indexets omkostnad.
Genomgång av diagnosen
Anta att orders har ett index på created_at, men att den här frågan ändå gör en sekventiell genomsökning:
Problemet är DATE(created_at). När kolumnen omsluts av en funktion kan indexet på den råa created_at inte användas. Lösningen är att skriva om frågan som ett intervallpredikat där kolumnen lämnas oförändrad, eller att skapa ett uttrycksindex på DATE(created_at).
-- Slow: function on the indexed column
WHERE DATE(created_at) = '2026-01-01'
-- Fast: bare column, range uses the index
WHERE created_at >= '2026-01-01'
AND created_at < '2026-01-02'Jämförelse av metoderna
Ha denna jämförelse i åtanke inför intervjun:
- Seq Scan, bäst när en stor andel av raderna returneras; sekventiell I/O.
- Index Scan, bäst för selektiva uppslagningar; genomgång av indexet plus slumpmässiga hämtningar från heapen.
- Bitmap Heap Scan, medelstort antal träffar; index till bitmap och därefter ordnade läsningar från heapen.
- Index-Only Scan, snabbast när indexet täcker alla kolumner som behövs och sidorna är all-visible.
Planeraren väljer utifrån uppskattad kostnad, som främst styrs av selektivitet och statistik.
Tvinga fram ett test (och varför inte i produktion)
För att bevisa en poäng under utveckling kan ni tillfälligt styra planeraren: SET enable_seqscan = off; tvingar den att föredra index, så att ni kan jämföra planer.
Detta är ett diagnostiskt knep, aldrig en lösning för produktion. Nämn i intervjuer att de verkliga lösningarna är bättre statistik, ett lämpligt index eller att skriva om predikatet, inte att globalt inaktivera planeringsfunktioner.
SET enable_seqscan = off;
EXPLAIN ANALYZE SELECT * FROM orders WHERE amount > 100;
SET enable_seqscan = on;Snabb kontroll
En fråga väljer endast email och filtrerar på email, och det finns ett B-trädsindex på email. Planen visar Index Only Scan. Varför är detta snabbare än en vanlig Index Scan?
Sammanfattning
Viktiga lärdomar om åtkomstmetoder:
- Seq Scan vinner för frågor med låg selektivitet; Index Scan vinner för selektiva frågor.
- Index-Only Scan undviker heapen när indexet täcker alla kolumner som behövs; håll utkik efter
Heap Fetchesoch visibility map. - Bitmap Heap Scan utgör en medelväg genom att hämta heapsidor i fysisk ordning.
- Planeraren fattar beslut utifrån selektivitet och statistik; funktioner på kolumner, typmismatch och inaktuell statistik är orsaker till att ett index ignoreras.
Lär dig Förberedelse inför kodningsintervjuer 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
- 90
- Lektioner
- 360
Vanliga frågor
Är lektionen ”Seq Scan jämfört med Index Scan och Index-Only” gratis?
Ja – hela texten till ”Seq Scan jämfört med Index Scan och Index-Only” 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örberedelse inför kodningsintervjuer, kan Ni uppgradera till CoddyKit PRO. Kursen i Förberedelse inför kodningsintervjuer innehåller totalt 4 lektioner.
Vad lär jag mig i ”Seq Scan jämfört med Index Scan och Index-Only”?
Förstå varför frågeplaneraren väljer varje alternativ och vad det säger om er fråga. Ni övar på Förberedelse inför kodningsintervjuer 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örberedelse inför kodningsintervjuer?
Du behöver inga förkunskaper. Utbildningen i Förberedelse inför kodningsintervjuer 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 2 av 4.
Hur lång tid tar lektionen ”Seq Scan jämfört med Index Scan och Index-Only”?
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örberedelse inför kodningsintervjuer-lektionen?
Ja. Varje Förberedelse inför kodningsintervjuer-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
- Läsa en EXPLAIN-plan
- Seq Scan jämfört med Index Scan och Index-Only
- Join-algoritmer: Nested Loop, Hash, Merge
- Identifiera och åtgärda långsamma frågor