MySQL LIMIT & OFFSET med exempel

⚡ Smart sammanfattning

Ocuco-landskapet MySQL Nyckelordet LIMIT begränsar hur många rader en fråga returnerar, och OFFSET-värdet avgör vilken rad resultatet börjar från. Tillsammans håller de resultatuppsättningarna små, gör att sidorna laddas snabbt och driver paginering post-för-post.

  • 🔢 Kärnbeteende: LIMIT N returnerar högst N rader. En tabell som innehåller färre rader än N returnerar alla rader utan fel.
  • 0️⃣ Nollfall: LIMIT 0 returnerar inga rader, vilket gör det till ett billigt sätt att inspektera kolumnmetadata.
  • 📍 Offset-syntax: LIMIT 1, 2 hoppar över en rad och returnerar två, så offseten skrivs först och radantalet sedan.
  • 📄 Pagineringsformel: OFFSET är lika med sidstorlek multiplicerad med sidnummer minus ett, vilket omvandlar en resultatuppsättning till numrerade sidor.
  • ↕️ Orderberoende: Utan BESTÄLLNING AV, MySQL kan returnera olika rader vid varje körning, så LIMIT är endast deterministisk med en explicit sortering.
  • ⚙️ Uttalandestöd: LIMIT begränsar också raderna som påverkas av UPDATE och DELETE, vilket skyddar en stor tabell från obegränsad skrivning.
  • ???? Prestandaförbehåll: En stor förskjutning gör MySQL läs och släng varje hoppad rad, så att djupa sidor växer långsammare.

MySQL GRÄNS och OFFSET

Vad är LIMIT-nyckelordet i MySQL?

Ocuco-landskapet BEGRÄNSA Nyckelordet begränsar antalet rader som returneras i ett frågeresultat. Det kan användas med SELECT-, UPDATE- och DELETE-satserna, så det begränsar antalet rader som en fråga läser såväl som antalet rader som en skrivning påverkar.

Syntaxen för LIMIT-nyckelordet är följande.

SELECT {fieldname(s) | *} FROM tableName(s) [WHERE condition] LIMIT N;

HÄR

  • "VÄLJ {fältnamn(n) | *} FRÅN tabellnamn" är SELECT-sats som innehåller de fält som vi skulle vilja returnera i vår förfrågan.
  • "[WHERE skick]" är valfritt, men när det anges anger det ett filter på resultatmängden. VAR klausul tillämpas före LIMIT, så filtrering sker först och taket tillämpas på det som överlever.
  • "GRÄNS N" är nyckelordet, och N är vilket tal som helst som börjar från 0. Om 0 anges som gränsvärde returneras inga poster alls. Om ett tal som 5 anges returneras fem poster. Om tabellen innehåller färre poster än N returneras alla och inget fel uppstår.

Syntaxen är kort, men anledningen till att den existerar är värd att ange före exemplen.

Varför ska vi använda nyckelordet LIMIT?

Anta att vi utvecklarping applikationen som körs ovanpå myflixdb. Systemdesignerna har bett oss att begränsa antalet poster som visas på en sida till 20 poster för att motverka långsamma laddningstider. Hur implementerar vi ett system som uppfyller ett sådant krav?

Nyckelordet LIMIT hanterar just denna situation. Istället för att hämta varje medlemsrad in i applikationen och ignorera de flesta av dem, returnerar frågan 20 poster per sida och databasen gör jobbet. Tre fördelar följer av det.

  • Snabbare svar: mindre data läses från disken och mindre data passerar nätverket.
  • Lägre minnesanvändning: Applikationen innehåller en sida med rader, inte hela tabellen.
  • Säkrare skriver: en GRÄNS för en UPPDATERING eller en RADERA ett kommando begränsar hur många rader ett misstag kan beröra.

MySQL LIMIT-frågeexempel

Exemplen nedan körs mot medlemstabellen i myflixdb-databasen. Det första returnerar två rader och inget mer.

SELECT * FROM members LIMIT 2;
medlemsnummer Fullständiga namn kön födelsedatum registreringsdatum fysisk adress postadress kontaktnummer e-mail kreditkortsnummer
1 Janet Jones Kvinna 21-07-1980 NULL First Street Tomt nr 4 Privat väska 0759 253 542 janetjones@yagoo.cm NULL
2 Janet Smith Jones Kvinna 23-06-1980 NULL Melrose 123 NULL NULL jj@fstreet.com NULL

Som resultatet ovan visar har endast två medlemmar återvänt.

Hämta en lista med tio (10) medlemmar från databasen

Anta att vi vill ha en lista över de första 10 registrerade medlemmarna från Myflix-databasen. Skriptet nedan frågar efter dem.

SELECT * FROM members LIMIT 10;

Att köra skriptet ger resultatet som visas nedan.

medlemsnummer Fullständiga namn kön födelsedatum registreringsdatum fysisk adress postadress kontaktnummer e-mail kreditkortsnummer
1 Janet Jones Kvinna 21-07-1980 NULL First Street Tomt nr 4 Privat väska 0759 253 542 janetjones@yagoo.cm NULL
2 Janet Smith Jones Kvinna 23-06-1980 NULL Melrose 123 NULL NULL jj@fstreet.com NULL
3 Robert Phil man 12-07-1989 NULL 3rd Street 34 NULL 12345 rm@tstreet.com NULL
4 Gloria Williams Kvinna 14-02-1984 NULL 2nd Street 23 NULL NULL NULL NULL
5 Leonard Hofstadter man NULL NULL Trästomme NULL 845738767 NULL NULL
6 Sheldon Cooper man NULL NULL Trästomme NULL 976736763 NULL NULL
7 Rajesh Koothrappali man NULL NULL Trästomme NULL 938867763 NULL NULL
8 Leslie Winkle man 14-02-1984 NULL Trästomme NULL 987636553 NULL NULL
9 Howard Wolowitz man 24-08-1981 NULL Southpark PO Box 4563 987786553 lwolowitz[at]email.me NULL

Endast 9 medlemmar har returnerats, eftersom N i LIMIT-klausulen är större än antalet poster i tabellen. Att begära 9 rader ger explicit samma resultatuppsättning.

SELECT * FROM members LIMIT 9;

💡 Tips: LIMIT väljer rader från den ordning servern råkar producera. Lägg till en SORTERA EFTER klausul närhelst radernas identitet har betydelse, annars är det inte garanterat att ”de första 10 medlemmarna” betyder samma nio personer två gånger.

Att begränsa radantalet är den första halvan av funktionen. Att välja var fönstret börjar är den andra.

Använda OFFSET-värdet i LIMIT-frågan

Ocuco-landskapet OFFSET värde används oftast tillsammans med nyckelordet LIMIT. Det anger vilken rad servern börjar hämta data från, så rader före den punkten hoppas över.

Anta att vi vill ha ett begränsat antal medlemmar med början från mitten av tabellen. Skriptet nedan börjar på andra raden och begränsar resultatet till två poster.

SELECT * FROM `members` LIMIT 1, 2;

Utför det i MySQL Arbetsbänk mot myflixdb ger följande resultat.

medlemsnummer Fullständiga namn kön födelsedatum registreringsdatum fysisk adress postadress kontaktnummer e-mail kreditkortsnummer
2 Janet Smith Jones Kvinna 23-06-1980 NULL Melrose 123 NULL NULL jj@fstreet.com NULL
3 Robert Phil man 12-07-1989 NULL 3rd Street 34 NULL 12345 rm@tstreet.com NULL

Observera att här FÖRSKYTTNING = 1, alltså är rad #2 den första raden som returneras, och GRÄNS = 2, därför kommer bara 2 poster tillbaka.

I formen med två argument skrivs offseten först och radantalet sedan, vilket är lätt att reversera av misstag. MySQL accepterar också en explicit form som tar bort tvetydigheten, och det är den att föredra i ny kod.

SELECT * FROM `members` LIMIT 2 OFFSET 1;

Båda satserna returnerar samma två rader. När offseten är förstådd faller pagineringsmönstret som varje listskärm förlitar sig på direkt ur den.

Hur man paginerar frågeresultat med LIMIT och OFFSET

Paginering delar upp en stor resultatmängd i numrerade sidor, och LIMIT tillsammans med OFFSET är den mekanism som gör det. Två värden styr varje sidförfrågan: sidstorleken, vilket är hur många poster som visas på en skärm, och sidnumret som begärs av användaren.

Offseten härleds från dem med en enda formel.

-- OFFSET = page_size * (page_number - 1)
SELECT membership_number, full_names
FROM members
ORDER BY membership_number ASC
LIMIT 20 OFFSET 0;   -- page 1

Sida 2 behåller samma gräns och flyttar förskjutningen framåt med en sidstorlek.

SELECT membership_number, full_names
FROM members
ORDER BY membership_number ASC
LIMIT 20 OFFSET 20;  -- page 2

Tre regler håller en paginerad lista korrekt och snabb.

  1. Sortera alltid: En paginerad fråga utan ORDER BY kan visa samma post på två olika sidor och dölja en annan helt, eftersom servern kan ändra radordningen mellan anrop.
  2. Sortera på en unik kolumn: Obligationer i sorteringskolumnen lämnar ordningen på de bundna raderna odefinierad. Att sortera på primärnyckeln, eller lägga till den som en oavgjord nyckel, eliminerar problemet.
  3. Titta på djupa sidor: FÖRSKJUTNING 100000 krafter MySQL att läsa hundratusen rader och kasta bort dem innan man återkommer till nästa tjugo. Svarstiden ökar med sidnumret.

För mycket djup paginering undviker nyckeluppsättningspaginering förskjutningen helt. Istället för att räkna rader att hoppa över, kommer frågan ihåg den sista nyckeln från föregående sida och frågar efter raderna efter den.

SELECT membership_number, full_names
FROM members
WHERE membership_number > 20      -- last id from the previous page
ORDER BY membership_number ASC
LIMIT 20;

Denna form förblir snabb oavsett djup, eftersom indexet hoppar direkt till starttangenten istället för att gå igenom raderna framför. Avvägningen är att sidorna måste gås igenom i ordning, så hoppaping direkt till sidan 500 är inte längre möjligt.

LIMIT i MySQL vs TOP och HÄMTA FÖRST

LIMIT finns inte i alla SQL-dialekter, vilket är viktigt så snart en fråga måste flyttas mellan databasmotorer. MySQL, PostgreSQLoch SQLite dela nyckelordet LIMIT. SQL Server använder TOP, och Oracle använder standardklausulen FETCH FIRST. Tabellen nedan jämför de tre.

Klausul Motor Exempelvis Hoppar över rader
GRÄNS … FÖRSKJUTNING MySQL, PostgreSQL, SQLite VÄLJ * FRÅN medlemmar GRÄNS 20 OFFSET 40; Ja, med OFFSET
TOPP SQL Server VÄLJ TOPP 20 * FRÅN medlemmar; Nej, OFFSET … FETCH krävs
HÄMTA FÖRST Oracle, Db2, standard SQL VÄLJ * FRÅN medlemmar HÄMTA ENDAST DE FÖRSTA 20 RADERNA; Ja, med FÖRSKJUTNING … RADER

Beteendet är detsamma i båda fallen: begränsa antalet rader och hoppa eventuellt över ett antal rader först. Endast stavningen ändras. En fråga som måste köras på mer än en motor bör därför isolera radbegränsande klausul snarare än att sprida den genom kodbasen.

Vanliga frågor

Ja. Båda accepterar ett vanligt radantal, till exempel RADERA FRÅN medlemmar GRÄNS 10. Offsetformen med två argument är inte tillåten där, så endast antalet berörda rader kan begränsas.

Offset räknas från noll, så OFFSET 0 börjar på den första raden och OFFSET 1 börjar på den andra. Själva radantalet är en vanlig kvantitet och läses som ett normalt tal.

Kör en separat SELECT COUNT(*) med samma WHERE-klausul men utan LIMIT. Antalet anger för applikationen hur många sidor som finns, medan den begränsade frågan returnerar raderna för den aktuella sidan.

Ofta, ja. AI-assistenter inuti klienter som MySQL Arbetsbänk Skriv om en OFFSET-fråga till en WHERE-sats på den senast sedda nyckeln. Bekräfta att sorteringskolumnen är unik och indexerad innan du litar på omskrivningen.

Eftersom den genererade satsen vanligtvis utelämnar ORDER BY. Utan en explicit sortering, MySQL kan returnera raderna i valfri ordning, så samma LIMIT kan producera ett annat exempel vid varje körning. Lägg till sorteringen själv.

Sammanfatta detta inlägg med: