Ja tens totes les peces d'una consulta menys una: decidir quantes files vols rebre. Amb les 20 files de productes sembla irrellevant, però el dia que et connectis a una taula de producció amb cinquanta milions de registres, un SELECT * FROM comandes; sense més pot col·lapsar el teu terminal, saturar la xarxa i fer que un administrador de sistemes et busqui amb cara de pocs amics. LIMIT és la primera línia de defensa. I és també la base de la paginació, un d'aquells problemes que semblen resolts en dos minuts i que en taules grans es converteixen en un maldecap clàssic. En aquesta lliçó aprendràs totes dues coses: l'ús quotidià i l'ús seriós.

Contingut

  1. LIMIT: acotar el resultat
  2. Per què LIMIT sense ORDER BY no és determinista
  3. OFFSET i la paginació clàssica
  4. Els dos problemes d'OFFSET en taules grans
  5. Paginació per cursor o keyset
  6. FETCH FIRST n ROWS ONLY: la forma estàndard
  7. Casos d'ús típics
  8. LIMIT a l'ordre lògic d'execució
  9. Errors habituals i consells
  10. Exercicis
  11. Conclusió

  1. LIMIT: acotar el resultat

LIMIT n indica quantes files, com a màxim, vols rebre. S'escriu al final de la consulta, després d'ORDER BY:

SELECT id, nom, preu
FROM productes
ORDER BY preu DESC
LIMIT 5;
id nom preu
15 Te verd matcha cerimonial 30 g 22.00
6 Crema facial d'àloe vera 50 ml 18.90
20 Càpsules d'espirulina 120 u 16.40
8 Oli corporal d'ametlles 200 ml 14.25
13 Espelmes de cera de soja (pack 2) 13.75

Els cinc productes més cars del catàleg. Aquest patró —ordenar i retallar— és la forma canònica de respondre a qualsevol pregunta de tipus "top N".

Comportament de LIMIT als casos límit:

Escriptura Què retorna
LIMIT 5 Com a molt 5 files
LIMIT 100 sobre productes Les 20 que hi ha. LIMIT és un màxim, no una exigència
LIMIT 0 Cap fila, però sí les capçaleres. Útil per inspeccionar els tipus de columna d'una consulta sense executar-la del tot
LIMIT ALL Totes. Equival a no posar-hi LIMIT; serveix per construir consultes per programa
LIMIT NULL Totes, igual que LIMIT ALL
LIMIT -1 ERROR: LIMIT must not be negative

L'ús més freqüent en el dia a dia ni tan sols porta ORDER BY: és fer un cop d'ull a una taula que no coneixes.

SELECT * FROM linies_comanda LIMIT 5;
id comanda_id producte_id quantitat preu_unitari descompte
1 1 1 2 11.95 0.00
2 1 2 3 3.90 0.00
3 1 14 2 3.25 0.00
4 2 6 1 17.50 0.00
5 2 9 2 4.60 0.00

Aquí SELECT * i l'absència d'ORDER BY són perfectament legítims: no vols unes files concretes, vols veure quina pinta tenen les dades. És exploració, no un informe.

Costum professional: quan et connectis a una base de dades que no coneixes, escriu LIMIT 10 abans d'escriure la resta de la consulta. Costa vuit caràcters i evita la vergonya de bloquejar una sessió en producció.

  1. Per què LIMIT sense ORDER BY no és determinista

Reprenem l'advertiment de 02-05, perquè amb LIMIT es torna molt més perillós.

SELECT id, nom, preu FROM productes LIMIT 3;
id nom preu
1 Oli d'oliva verge extra 500 ml 12.50
2 Arròs integral ecològic 1 kg 3.90
3 Mel de tarongina crua 500 g 9.75

Què has demanat exactament? Tres files qualssevol. No les tres primeres per id, no les tres més barates: tres files arbitràries, les que el motor tingués més a mà. Que avui en surtin la 1, la 2 i la 3 és casualitat de l'ordre físic.

La diferència amb una consulta sense LIMIT és subtil però crucial:

Consulta Sense ORDER BY
SELECT ... FROM productes Retorna les 20 files, en ordre impredictible. El conjunt és correcte; només l'ordre és incert
SELECT ... FROM productes LIMIT 3 Retorna tres files impredictibles. El conjunt mateix és incert

En el primer cas, ordenar el resultat a la teva aplicació arregla el problema. En el segon no hi ha cap arranjament possible: has perdut 17 files i no saps quines.

Regla: LIMIT sense ORDER BY només és acceptable per explorar. Tan bon punt el resultat es faci servir per a alguna cosa, l'ORDER BY és obligatori, i ha de ser determinista (acabat en una columna única, com vas veure a 02-05).

  1. OFFSET i la paginació clàssica

OFFSET m descarta les primeres m files del resultat abans d'aplicar LIMIT. Combinats, permeten recórrer un resultat gran a trossos:

Pàgina N  →  LIMIT mida OFFSET (N - 1) * mida

Vegem-ho amb el catàleg de BotigaVerda ordenat per preu descendent i pàgines de cinc productes.

Pàgina 1LIMIT 5 OFFSET 0:

SELECT id, nom, preu
FROM productes
ORDER BY preu DESC, id
LIMIT 5 OFFSET 0;
id nom preu
15 Te verd matcha cerimonial 30 g 22.00
6 Crema facial d'àloe vera 50 ml 18.90
20 Càpsules d'espirulina 120 u 16.40
8 Oli corporal d'ametlles 200 ml 14.25
13 Espelmes de cera de soja (pack 2) 13.75

Pàgina 2LIMIT 5 OFFSET 5:

id nom preu
1 Oli d'oliva verge extra 500 ml 12.50
10 Detergent ecològic concentrat 1 L 11.20
12 Bosses reutilitzables de cotó (pack 5) 9.90
3 Mel de tarongina crua 500 g 9.75
7 Xampú sòlid de romaní 80 g 8.40

Pàgina 3LIMIT 5 OFFSET 10:

id nom preu
19 Desodorant natural en barra 50 g 7.80
11 Fregall vegetal de lufa (pack 3) 5.50
17 Suc de taronja premsat en fred 1 L 5.40
16 Kombutxa de gingebre 750 ml 4.95
9 Bàlsam labial de calèndula 15 ml 4.60

I la quarta i última tancaria amb els productes 2, 18, 14, 4 i 5.

Resum del càlcul:

Pàgina OFFSET LIMIT Productes retornats
1 0 5 15, 6, 20, 8, 13
2 5 5 1, 10, 12, 3, 7
3 10 5 19, 11, 17, 16, 9
4 15 5 2, 18, 14, 4, 5

Detalls importants:

  • L'ORDER BY és obligatori. Sense ell, cada pàgina es calcula sobre un ordre diferent i podries veure el mateix producte a dues pàgines i un altre a cap.
  • L'ORDER BY ha de ser determinista. Per això hem escrit ORDER BY preu DESC, id: si dos productes costessin el mateix, el desempat per id garanteix que sempre caiguin a la mateixa pàgina.
  • OFFSET sense LIMIT és vàlid: OFFSET 15 retorna les files de la 16 endavant.
  • OFFSET més gran que el total retorna zero files, sense error. OFFSET 100 sobre productes no dona res.

  1. Els dos problemes d'OFFSET en taules grans

Aquesta paginació funciona, és la que aprèn tothom, i té dos defectes seriosos que només es manifesten quan les dades creixen.

4.1. El cost creix amb el número de pàgina

OFFSET m no salta les primeres m files: les calcula i les descarta. El motor no té manera d'endevinar quina és la fila número 500 001 sense haver produït les 500 000 anteriors.

Pàgina Files que el motor produeix Files que et lliura
1 20 20
50 1 000 20
500 10 000 20
50 000 1 000 000 20

L'última pàgina d'un llistat gran pot trigar centenars de vegades més que la primera. És un patró conegut: els usuaris es queixen que "el web va lent al final del catàleg", i la causa és aquí. Amb EXPLAIN ANALYZE (mòdul 8) es veu amb tota claredat al node Limit, que informa de quantes files ha descartat.

4.2. Les dades es mouen entre pàgina i pàgina

Aquest és pitjor, perquè no és lent: és incorrecte.

Imagina que un usuari està veient la pàgina 1 del catàleg ordenat per preu descendent i, en aquell instant, algú dona d'alta un producte de 25 € (més car que el matcha). Quan l'usuari premi "següent":

Moment Què passa
Pàgina 1 (abans) 15, 6, 20, 8, 13
S'insereix un producte nou de 25.00 € Tot el llistat es desplaça una posició
Pàgina 2 (OFFSET 5) Ara la posició 6 l'ocupa el producte 13, que ja era a la pàgina 1

L'usuari veu el producte 13 dues vegades. I amb un esborrat passa el contrari: una fila desapareix sense haver-se mostrat mai.

Canvi a les dades Símptoma per a l'usuari
S'insereix una fila que va abans de la pàgina actual Veu una fila repetida
S'esborra una fila anterior a la pàgina actual Una fila se salta i no la veu mai

Cada pàgina és una consulta independent, executada en un moment diferent i sobre un estat diferent de la taula. OFFSET no té memòria del que ja et va ensenyar.

Quan es pot conviure amb OFFSET?

Escenari OFFSET és acceptable?
Panell intern amb pocs milers de files Sí, sense problema
Dades que no canvien durant la sessió (un informe històric)
Necessites "anar a la pàgina 47" directament Sí: és l'únic que ho permet
Catàleg públic amb milions de files i escriptures constants No
Un scroll infinit en una aplicació mòbil No
Exportar una taula sencera a trossos No: fes servir keyset

  1. Paginació per cursor o keyset

L'alternativa consisteix a deixar de dir "salta't 500 000 files" i començar a dir "dona'm el que ve després d'això". En comptes d'una posició, es recorda l'últim valor vist.

Tornem al nostre catàleg. La pàgina 1 acabava amb el producte 13, amb preu 13.75 €. La pàgina 2 es demana així:

SELECT id, nom, preu
FROM productes
WHERE preu < 13.75
ORDER BY preu DESC, id
LIMIT 5;
id nom preu
1 Oli d'oliva verge extra 500 ml 12.50
10 Detergent ecològic concentrat 1 L 11.20
12 Bosses reutilitzables de cotó (pack 5) 9.90
3 Mel de tarongina crua 500 g 9.75
7 Xampú sòlid de romaní 80 g 8.40

Idèntica a la pàgina 2 de la secció 3, però obtinguda sense descartar res: el motor va directe a les files que compleixen preu < 13.75.

Què passa si hi ha empats. Si dos productes costessin exactament 13.75 €, WHERE preu < 13.75 es saltaria el segon. La solució és comparar la tupla completa de les columnes d'ordenació, cosa que SQL permet:

SELECT id, nom, preu
FROM productes
WHERE (preu, id) < (13.75, 13)
ORDER BY preu DESC, id DESC
LIMIT 5;

La comparació (preu, id) < (13.75, 13) és lexicogràfica: es compleix si preu < 13.75, o si preu = 13.75 i a més id < 13. És exactament la condició "estrictament després de l'últim element vist" per a aquest ordre. Compte amb un detall: perquè la comparació de tuples encaixi, totes les columnes de l'ORDER BY han d'anar en el mateix sentit, i per això aquí hi apareix id DESC.

Comparativa dels dos enfocaments:

Aspecte OFFSET Keyset
Cost de la pàgina N Creix linealment amb N Constant
Aprofita un índex? Només per ordenar Sí, per posicionar-se directament
Files repetides o saltades si les dades canvien No
Permet saltar a la pàgina 47? No: només "següent" i "anterior"
Permet mostrar "pàgina 3 de 120"? No sense una consulta addicional
Complexitat d'implementació Trivial Mitjana: cal arrossegar el cursor

A la pràctica: si la teva interfície és un scroll infinit o un botó "carrega'n més", el keyset és sempre la resposta correcta. Si necessites numerets de pàgina clicables, OFFSET és l'únic viable i cal assumir-ne els límits (o limitar el nombre de pàgines navegables, que és el que fan gairebé tots els cercadors).

Perquè el keyset rendeixi cal un índex sobre les columnes d'ordenació, en aquest cas (preu, id). Sense ell, PostgreSQL ha d'ordenar tota la taula igualment i no hi guanyes res. Els índexs són el mòdul 8.

  1. FETCH FIRST n ROWS ONLY: la forma estàndard

LIMIT és còmode, universalment conegut... i no és SQL estàndard. El va introduir MySQL, el va adoptar PostgreSQL i avui l'entenen gairebé tots els motors, però la sintaxi oficial de l'estàndard SQL:2008 és una altra:

SELECT id, nom, preu
FROM productes
ORDER BY preu DESC, id
OFFSET 0 ROWS
FETCH FIRST 5 ROWS ONLY;
id nom preu
15 Te verd matcha cerimonial 30 g 22.00
6 Crema facial d'àloe vera 50 ml 18.90
20 Càpsules d'espirulina 120 u 16.40
8 Oli corporal d'ametlles 200 ml 14.25
13 Espelmes de cera de soja (pack 2) 13.75

Exactament el mateix resultat. PostgreSQL admet totes dues formes i les tracta igual.

PostgreSQL afegeix a més WITH TIES, que amplia el resultat per incloure totes les files empatades amb l'última:

SELECT id, nom, preu
FROM productes
ORDER BY preu DESC
FETCH FIRST 5 ROWS WITH TIES;

Sobre aquestes dades retorna les mateixes 5 files, perquè no hi ha dos productes amb el mateix preu. Però si hi hagués tres productes a 13.75 €, WITH TIES retornaria 7 files en comptes de 5: és la forma correcta de fer un "top 5" honest en una competició. WITH TIES exigeix ORDER BY i no funciona amb LIMIT, només amb FETCH.

Taula comparativa entre motors:

Motor Sintaxi principal Alternatives
Estàndard SQL:2008 OFFSET m ROWS FETCH FIRST n ROWS ONLY
PostgreSQL LIMIT n OFFSET m FETCH FIRST n ROWS ONLY, WITH TIES
MySQL / MariaDB LIMIT n OFFSET m LIMIT m, n (els arguments al revés!)
SQLite LIMIT n OFFSET m LIMIT m, n
SQL Server 2012+ OFFSET m ROWS FETCH NEXT n ROWS ONLY SELECT TOP (n) ... (sense offset)
Oracle 12c+ OFFSET m ROWS FETCH FIRST n ROWS ONLY
Oracle 11g i anteriors WHERE ROWNUM <= n sobre una subconsulta ordenada

Dos paranys d'aquesta taula que convé subratllar:

  1. LIMIT m, n de MySQL inverteix el significat: el primer número és el desplaçament i el segon la quantitat. LIMIT 5, 10 a MySQL és LIMIT 10 OFFSET 5 a PostgreSQL. Una consulta copiada sense llegir-la retorna dades equivocades.
  2. ROWNUM d'Oracle s'assigna abans de l'ORDER BY. WHERE ROWNUM <= 5 ORDER BY preu DESC retorna cinc files qualssevol i després les ordena: no és el top 5. Cal ordenar en una subconsulta i aplicar ROWNUM a fora.

Quina fer servir? En aquest curs, LIMIT: és el que veuràs al 99 % del codi PostgreSQL. Si escrius SQL que s'hagi d'executar en diversos motors, OFFSET ... FETCH FIRST ... ROWS ONLY és l'aposta segura.

  1. Casos d'ús típics

7.1. Top N

Ja ho has vist amb els productes més cars. Una altra variant, els cinc de més marge:

SELECT nom,
       preu,
       cost,
       preu - cost AS marge
FROM productes
WHERE actiu
ORDER BY marge DESC, id
LIMIT 5;
nom preu cost marge
Te verd matcha cerimonial 30 g 22.00 12.50 9.50
Crema facial d'àloe vera 50 ml 18.90 9.50 9.40
Oli corporal d'ametlles 200 ml 14.25 7.10 7.15
Espelmes de cera de soja (pack 2) 13.75 6.90 6.85
Bosses reutilitzables de cotó (pack 5) 9.90 4.30 5.60

Fixa't que les Càpsules d'espirulina (marge 7.70 €, tercera del catàleg) no hi apareixen: el WHERE actiu les descarta abans d'ordenar. L'ordre lògic mana: primer es filtra, després s'ordena, i només al final es retalla.

7.2. Els últims registres

SELECT id, client_id, data_comanda, estat, metode_pagament
FROM comandes
ORDER BY data_comanda DESC, id DESC
LIMIT 3;
id client_id data_comanda estat metode_pagament
20 9 2026-02-21 pendent contrareemborsament
19 6 2026-02-09 pagat targeta
18 5 2026-01-27 pagat transferencia

Les tres últimes comandes rebudes: el contingut natural d'un panell d'"activitat recent".

7.3. El registre extrem

SELECT id, nom, cognoms, data_registre
FROM clients
ORDER BY data_registre
LIMIT 1;
id nom cognoms data_registre
1 Lucía Martínez Soler 2025-01-10

La primera clienta de BotigaVerda. Aquest patró —ORDER BY ... LIMIT 1— és equivalent a fer servir MIN/MAX, però amb un avantatge: et retorna la fila sencera, no només el valor mínim. Amb MIN(data_registre) sabries la data, però no qui és. Les funcions d'agregació arriben a la lliçó 04-04.

7.4. Mostreig ràpid per a exploració

SELECT * FROM ressenyes LIMIT 3;
id producte_id client_id puntuacio comentari data
1 1 1 5 Oli excel·lent, gust intens i envàs molt cuidat. 2025-03-15
2 2 1 4 Bon arròs, tot i que triga una mica més a bullir del normal. 2025-03-16
3 6 2 5 La crema deixa la pell molt suau. Repetiré sens dubte. 2025-03-25

  1. LIMIT a l'ordre lògic d'execució

Amb LIMIT es completa el cicle que vam començar a 02-01. Aquest és el diagrama definitiu del mòdul:

flowchart LR
    A["1 · FROM<br/>origen de les files"] --> B["2 · WHERE<br/>filtra files"]
    B --> C["3 · SELECT<br/>projecta i calcula<br/>neixen els àlies"]
    C --> D["3b · DISTINCT<br/>elimina duplicats"]
    D --> E["4 · ORDER BY<br/>ordena el resultat"]
    E --> F["5 · LIMIT / OFFSET<br/>retalla"]

LIMIT és sempre l'últim. D'aquí en surten conseqüències que convé tenir clares:

Pregunta Resposta
LIMIT 5 fa que WHERE examini només 5 files? No. WHERE s'aplica a totes les files de la taula
LIMIT 5 amb ORDER BY ordena només 5 files? No. Lògicament s'ordena tot i després es retalla
Aleshores, LIMIT no estalvia feina? Sí que n'estalvia, però al pla físic, no al lògic

Aquest últim punt mereix un matís. Encara que lògicament s'ordeni tot, PostgreSQL és més llest que això: quan veu un ORDER BY ... LIMIT n petit, fa servir un algorisme anomenat top-N heapsort, que manté a la memòria només les n millors files vistes fins al moment en comptes d'ordenar el conjunt sencer. I si existeix un índex que ja retorna les files en l'ordre demanat, pot llegir les n primeres i aturar-se, sense tocar la resta de la taula.

És l'exemple perfecte de la distinció de 02-01: l'ordre lògic defineix el significat de la consulta, i el pla físic que tria l'optimitzador pot ser radicalment més eficient mentre produeixi el mateix resultat. Ho veuràs amb els teus propis ulls al mòdul 8 amb EXPLAIN.

Errors habituals i consells

  • LIMIT sense ORDER BY en qualsevol consulta que no sigui exploratòria. Retorna files arbitràries i el problema no es pot arreglar després.
  • ORDER BY no determinista en paginar. Si hi ha empats i no els desempates amb una columna única, una mateixa fila pot aparèixer a dues pàgines i una altra a cap.
  • Copiar LIMIT 10, 20 d'un exemple de MySQL. A MySQL significa "20 files des de l'11"; a PostgreSQL ni tan sols és sintaxi vàlida.
  • Creure que OFFSET salta files sense cost. Les produeix i les llença. A la pàgina 5 000 ho notaràs.
  • Paginar amb OFFSET sobre dades que canvien. Files repetides i files saltades, sense cap error que ho delati.
  • Aplicar el keyset amb un ORDER BY que no coincideix amb la condició del WHERE. Les columnes han de ser les mateixes, en el mateix ordre i en el mateix sentit.
  • Fer servir LIMIT per "arreglar" una consulta lenta. Si la consulta és lenta per manca d'índex, LIMIT pot continuar sent lent: el motor ha de trobar les files abans de retallar-les.
  • Esperar que LIMIT 1 substitueixi un WHERE ben escrit. Retornar una fila qualsevol de les que compleixen la condició rarament és el que es vol.
  • Consell: LIMIT primer, consulta després. En explorar una base desconeguda, escriu-lo abans de res.
  • Consell: LIMIT 0 és útil. Et dona les columnes i els seus tipus sense portar dades, ideal per comprovar la forma d'una consulta complexa.
  • Consell: per a un "top N" honest, planteja't FETCH FIRST n ROWS WITH TIES. Tallar pel número 5 exacte quan el 5 i el 6 empaten és enganyós.

Exercicis

Exercici 1

Atenció al client necessita un panell amb les cinc comandes més antigues que encara no estan lliurades ni cancel·lades, mostrant id, client_id, data_comanda, estat i despeses_enviament. Escriu la consulta i explica quantes files retorna realment i per què.

Exercici 2

Construeix la segona pàgina d'un llistat de clients ordenat per país i, dins de cada país, per cognoms, amb pàgines de quatre clients. Escriu-la primer amb OFFSET i després amb paginació keyset. Explica quina informació necessita l'aplicació en cada cas per demanar la pàgina següent.

Exercici 3

L'equip de compres vol les tres línies de comanda de més import. Escriu la consulta fent servir la sintaxi estàndard FETCH FIRST, i indica què canviaria si fessis servir WITH TIES. Després respon: per què aquesta consulta no et pot dir de quin producte es tracta?

Solucions

Solució 1

SELECT id,
       client_id,
       data_comanda,
       estat,
       despeses_enviament
FROM comandes
WHERE estat <> 'lliurat'
  AND estat <> 'cancellat'
ORDER BY data_comanda, id
LIMIT 5;
id client_id data_comanda estat despeses_enviament
16 4 2025-12-19 enviat 4.95
17 7 2026-01-13 enviat 9.90
18 5 2026-01-27 pagat 4.95
19 6 2026-02-09 pagat 4.95
20 9 2026-02-21 pendent 12.50

5 files, que resulten ser totes les que compleixen la condició: de les 20 comandes, 14 estan lliurades i 1 cancel·lada, així que només en queden 5 en curs. El LIMIT 5 no ha retallat res, i aquest és un comportament normal: LIMIT és un màxim, no una promesa.

El raonament per l'ordre lògic: FROM porta 20 files → WHERE en deixa 5 → SELECT projecta → ORDER BY data_comanda, id les ordena de més antiga a més recent → LIMIT 5 no en descarta cap. Si demà entren deu comandes noves, la consulta continuarà retornant les cinc més antigues sense tocar-hi ni una coma.

Al mòdul 4 escriuràs aquesta condició de manera més neta com a WHERE estat NOT IN ('lliurat', 'cancellat').

Solució 2

Amb OFFSET, la pàgina 2 (clients 5 a 8 del llistat):

SELECT id, nom, cognoms, ciutat, pais
FROM clients
ORDER BY pais, cognoms, id
LIMIT 4 OFFSET 4;

El llistat complet ordenat per pais, cognoms comença així: Belmonte Roca (5), Bosch Ferrer (13), Carrasco Vega (15), Ferrer Ibáñez (2) —pàgina 1—, i continua:

id nom cognoms ciutat pais
14 Hugo Iglesias Pardo Saragossa Espanya
6 Pau Llorens Vidal València Espanya
1 Lucía Martínez Soler València Espanya
11 Elena Navarro Puig Alacant Espanya

Amb paginació keyset, partint de l'últim element de la pàgina 1 —Carlos Ferrer Ibáñez, país Espanya, cognoms Ferrer Ibáñez, id 2—:

SELECT id, nom, cognoms, ciutat, pais
FROM clients
WHERE (pais, cognoms, id) > ('Espanya', 'Ferrer Ibáñez', 2)
ORDER BY pais, cognoms, id
LIMIT 4;

Retorna exactament les mateixes quatre files.

Què necessita l'aplicació en cada cas:

Enfocament Què arrossega entre peticions
OFFSET Només un número: la pàgina actual. Fàcil de posar en una URL (?page=2) i permet saltar a qualsevol pàgina
Keyset Els valors d'ordenació de l'última fila mostrada (aquí pais, cognoms i id). Es desen en un "cursor" que l'aplicació retorna en demanar la pàgina següent

Fixa't en dos detalls del keyset: la tupla del WHERE conté exactament les mateixes columnes de l'ORDER BY i en el mateix ordre, i s'hi inclou id com a última columna precisament per desempatar dos clients que compartissin país i cognoms. Sense aquest id, un cognom repetit faria que es perdés un client entre pàgina i pàgina.

Solució 3

SELECT id,
       comanda_id,
       quantitat,
       preu_unitari,
       descompte,
       ROUND(quantitat * preu_unitari * (1 - descompte), 2) AS import
FROM linies_comanda
ORDER BY quantitat * preu_unitari * (1 - descompte) DESC, id
FETCH FIRST 3 ROWS ONLY;
id comanda_id quantitat preu_unitari descompte import
28 12 2 22.00 0.00 44.00
18 8 3 12.50 0.05 35.63
24 10 2 18.90 0.10 34.02

Què canviaria amb WITH TIES. Res, en aquest cas: la quarta línia val 26.73 €, molt lluny dels 34.02 € de la tercera, així que no hi ha cap empat a arrossegar. Però convé notar que WITH TIES no pot portar un desempat artificial a l'ORDER BY: si hi deixes el , id final, cada fila té un valor d'ordenació únic i mai no hi haurà empats a incloure. Perquè WITH TIES serveixi d'alguna cosa cal ordenar només pel criteri real:

ORDER BY quantitat * preu_unitari * (1 - descompte) DESC
FETCH FIRST 3 ROWS WITH TIES;

Amb aquestes dades retorna les mateixes 3 files. Si hi hagués dues línies empatades a 34.02 €, en retornaria 4.

Per què no pots saber de quin producte es tracta. Perquè linies_comanda desa producte_id, un número, i el nom del producte viu a la taula productes. Amb les eines d'aquest mòdul només pots consultar una taula alhora: el màxim que pots dir és que la línia 28 correspon al producte 15. Per escriure "Te verd matcha cerimonial 30 g" a l'informe cal combinar totes dues taules, i això és precisament el que comença a la lliçó següent.

Conclusió

Has tancat el cicle complet d'una consulta:

  • LIMIT n acota el resultat a un màxim de n files i és la primera línia de defensa en explorar taules grans o desconegudes.
  • LIMIT sense ORDER BY no és determinista: retorna files arbitràries, i aquest dany no es pot reparar després.
  • OFFSET m descarta les primeres m files i permet la paginació clàssica LIMIT mida OFFSET (N-1)*mida, que exigeix un ORDER BY determinista.
  • Aquesta paginació té dos defectes en taules grans: el cost creix amb el número de pàgina, i les insercions o esborrats fan que es repeteixin o se saltin files.
  • La paginació per cursor o keysetWHERE (columnes) < (últims valors vistos)— té cost constant i no es descompensa, a canvi de no poder saltar a una pàgina arbitrària.
  • FETCH FIRST n ROWS ONLY és la forma estàndard, i WITH TIES amplia el resultat amb les files empatades. Cada motor té el seu dialecte, i LIMIT m, n de MySQL inverteix els arguments.
  • LIMIT és el pas 5 i últim de l'ordre lògic; l'optimitzador, en canvi, sí que aprofita la seva presència amb estratègies com el top-N heapsort.

I amb això tanques el mòdul 2 complet. Saps construir una consulta de principi a fi: triar-ne l'origen amb FROM, filtrar files amb WHERE, projectar i calcular columnes amb SELECT i els seus àlies, eliminar repeticions amb DISTINCT, imposar un ordre amb ORDER BY i retallar el resultat amb LIMIT. I saps en quin ordre lògic passa tot això, que és el que t'ha permès entendre per què un àlies funciona en un lloc i en un altre no.

Però fixa't en el sostre amb el qual has topat una vegada i una altra: comandes et diu client_id = 9 i no "Camille Dubois"; linies_comanda et diu producte_id = 15 i no "Te verd matcha cerimonial"; productes et diu categoria_id = 2 i no "Cosmètica natural". Totes les teves consultes han mirat una sola taula, i les preguntes que de debò interessen a BotigaVerda —què va comprar cada client, quina categoria factura més, quin comercial tanca més comandes, quins productes no ha comprat ningú— viuen precisament a les relacions entre taules que vas dibuixar al diagrama de 01-06. Al mòdul 3, Consultes amb múltiples taules, aprendràs a recórrer aquestes relacions amb JOIN: l'INNER JOIN per al que casa a banda i banda, el LEFT i el RIGHT per conservar el que no casa —allà apareixeran per fi els tres clients sense comandes i els tres productes mai venuts—, el FULL OUTER per a totes dues coses alhora, el SELF JOIN per a les relacions reflexives d'empleats i clients, i UNION, INTERSECT i EXCEPT per combinar resultats sencers. Les nou taules de BotigaVerda deixen de ser nou illes.

Curs de SQL

Mòdul 1: Introducció a SQL

Mòdul 2: Consultes bàsiques de SQL

Mòdul 3: Treballar amb múltiples taules

Mòdul 4: Filtratge avançat de dades

Mòdul 5: Manipulació de dades

Mòdul 6: Funcions avançades de SQL

Mòdul 7: Subconsultes i consultes imbricades

Mòdul 8: Índexs i optimització del rendiment

Mòdul 9: Transaccions i concurrència

Mòdul 10: Temes avançats

Mòdul 11: SQL a la pràctica

Mòdul 12: Projecte final

© Copyright 2026. Tots els drets reservats