flowchart TD
A([Inici]) --> B{"Condició<br/>certa?"}
B -->|Sí| C["Instruccions<br/>del bloc"]
B -->|No| D["Se salta el bloc"]
C --> E([Continua])
D --> E
6 Estructures de selecció
Objectius
- Entendre què és una estructura de selecció i per què un programa ha de “prendre decisions”.
- Escriure condicions amb
if,if-elsei cadeneselse if. - Construir condicions booleanes amb operadors relacionals i lògics.
- Triar entre molts camins amb
switch, tant en la forma clàssica com en la moderna (->). - Fer servir l’operador ternari per a decisions curtes.
- Reconèixer i evitar els errors típics: confondre
==amb=i oblidar elbreakalswitch.
Fins ara els nostres programes s’executaven sempre igual, de dalt a baix. Però un programa útil ha de reaccionar: si la nota és un 5 o més, aprovat; si no, suspès. Si l’usuari escriu “sí”, continuem; si no, parem. Aquesta capacitat de triar un camí o un altre segons una condició és el que aporten les estructures de selecció, la base de tota la lògica que vindrà (i que combinarem amb els bucles).
6.1 Prendre decisions
Una estructura de selecció (o condicional) permet que un programa executi unes instruccions només si es compleix una condició.
La condició és sempre una expressió booleana: una pregunta amb resposta true (cert) o false (fals).
Quan arribes a un encreuament, no camines sempre igual: mires el semàfor. Si està verd, passes; si no, esperes. La teva acció depèn d’una condició.
Un programa amb if fa exactament això: comprova una condició i actua en conseqüència.
6.2 Condicions booleanes
Abans de decidir, cal saber escriure la pregunta. Una condició es construeix amb:
- Operadors relacionals: comparen dos valors.
- Operadors lògics: combinen condicions.
| Operador | Significat | Exemple | Resultat |
|---|---|---|---|
== |
igual a | edat == 18 |
Cert si val 18 |
!= |
diferent de | nota != 0 |
Cert si no és 0 |
>, < |
més gran / més petit | preu > 100 |
|
>=, <= |
més gran o igual / més petit o igual | nota >= 5 |
|
&& |
i (les dues certes) | edat >= 18 && teCarnet |
|
|| |
o (almenys una certa) | esFestiu || esCapDeSetmana |
|
! |
no (nega) | !estaObert |
Exemple mínim. Combinar condicions per decidir si algú pot conduir:
int edat = 20;
boolean teCarnet = true;
boolean potConduir = edat >= 18 && teCarnet; // true només si totes dues
System.out.println("Pot conduir? " + potConduir);== amb =
No podem confondre els dos operadors:
- Operador
=assigna un valor - Operador
==compara.
int x = 5; // assignació: posa 5 dins de x
if (x == 5) { } // comparació: x val 5?En Java, escriure if (x = 5) dona error de compilació amb enters (perquè x = 5 no és un booleà), cosa que t’ajuda a detectar-ho.
Però amb booleans if (obert = true) sí que compila i és un error lògic silenciós: assigna true a obert en comptes de comparar. Escriu sempre == per comparar.
6.3 El if simple
La forma més bàsica: executa un bloc només si la condició és certa.
if (condició) {
// instruccions que s'executen només si la condició és certa
}Exemple: avisar si un dipòsit té poca benzina:
int litres = 3;
if (litres < 5) {
System.out.println("Atenció: queda poc combustible!");
}
System.out.println("Fi de la comprovació.");Si litres fos 10, el missatge d’atenció no apareixeria, però “Fi de la comprovació.” sempre s’escriu, perquè és fora del bloc.
No posis mai punt i coma just després del if:
if (litres < 5); // ⟵ aquest ; buida el if!
{
System.out.println("Atenció!"); // s'executa SEMPRE
}El ; tanca el if amb un cos buit, i el bloc de sota es converteix en codi normal que s’executa sempre. És un error molt difícil de veure.
6.4 El if-else
Quan volem fer una cosa si es compleix i una altra de diferent si no, afegim else.
if (condició) {
// camí A: condició certa
} else {
// camí B: condició falsa
}Exemple: decidir aprovat o suspès:
int nota = 4;
if (nota >= 5) {
System.out.println("Aprovat!");
} else {
System.out.println("Suspès. A repassar.");
}Exactament un dels dos blocs s’executa sempre: mai els dos, mai cap.
Demana un nombre enter amb Scanner i escriu si és parell o senar. Pista: un nombre és parell si n % 2 == 0.
6.5 Encadenament de else if
Sovint hi ha més de dos camins. Per triar entre diverses opcions excloents, encadenem else if.
Java comprova les condicions de dalt a baix i executa el primer bloc la condició del qual sigui certa; la resta les ignora.
int nota = 7;
if (nota < 5) {
System.out.println("Suspès");
} else if (nota < 7) {
System.out.println("Aprovat");
} else if (nota < 9) {
System.out.println("Notable");
} else {
System.out.println("Excel·lent");
}Fixa’t que a la segona branca no cal escriure nota >= 5 && nota < 7: si hem arribat allà, és que la primera condició (nota < 5) ja era falsa, així que nota >= 5 es dona per descomptat.
L’ordre importa. Si poses les condicions “a l’inrevés”, una de més general pot capturar casos que volies tractar a part:
if (nota >= 5) {
System.out.println("Aprovat");
} else if (nota >= 9) { // MAI s'hi arriba amb un 9!
System.out.println("Excel·lent"); // un 9 ja ha entrat a "Aprovat"
}Ordena de la condició més restrictiva a la més general, o revisa bé els llindars.
6.6 L’estructura switch
Quan comparem una mateixa variable amb molts valors concrets, una llarga cadena de else if es fa pesada.
El switch ho expressa de manera més neta. Hi ha dues formes:
- La clàssica.
- La moderna.
Estructura switch clàssica
La forma tradicional fa servir case, break i default:
int dia = 3;
switch (dia) {
case 1:
System.out.println("Dilluns");
break;
case 2:
System.out.println("Dimarts");
break;
case 3:
System.out.println("Dimecres");
break;
default:
System.out.println("Un altre dia");
}- Cada
caseés un valor possible de la variable. - El
breaksurt delswitchun cop fet el bloc. - El
defaultrecull tots els casos no previstos (com unelsefinal).
break
Al switch clàssic, si t’oblides el break, l’execució continua caient cap als case següents (això s’anomena fall-through):
switch (dia) {
case 1:
System.out.println("Dilluns");
// sense break!
case 2:
System.out.println("Dimarts"); // també s'escriu si dia == 1!
break;
}Amb dia == 1 s’escriuen Dilluns I Dimarts. Aquesta és la font d’errors número u del switch clàssic. La forma moderna l’elimina de soca-rel.
Estructura switch moderna
Des de Java 14, la fletxa -> fa el switch molt més segur i curt: no hi ha fall-through i, per tant, no calen break.
int dia = 3;
switch (dia) {
case 1 -> System.out.println("Dilluns");
case 2 -> System.out.println("Dimarts");
case 3 -> System.out.println("Dimecres");
default -> System.out.println("Un altre dia");
}A més, el switch modern pot retornar un valor (aleshores s’anomena switch expression) i agrupar diversos valors amb comes:
String tipus = switch (dia) {
case 6, 7 -> "Cap de setmana";
default -> "Dia laborable";
};
System.out.println(tipus);Compara les dues formes:
| Aspecte | switch clàssic |
switch modern (->) |
|---|---|---|
| Sintaxi de cada cas | case X: … break; |
case X -> ... |
| Fall-through (cau al següent) | Sí (font d’errors) | No (segur) |
| Agrupar valors | Repetint case |
case 1, 2, 3 -> |
| Pot retornar un valor | No directament | Sí (switch expression) |
| Recomanació | Codi antic | Preferible en codi nou |
Escriu un switch modern que rebi un int mes (1–12) i retorni l’estació de l’any com a String. Agrupa els mesos amb comes (per exemple, case 12, 1, 2 -> "Hivern").
6.7 L’operador ternari
Per a decisions molt curtes que només trien entre dos valors, hi ha una drecera: l’operador ternari ? :.
Es llegeix “condició ? valor si cert : valor si fals”.
int nota = 6;
String resultat = (nota >= 5) ? "Aprovat" : "Suspès";
System.out.println(resultat);És equivalent a un if-else que només assigna una variable, però en una sola línia. Compara:
// Amb if-else (4 línies)
String r;
if (nota >= 5) { r = "Aprovat"; } else { r = "Suspès"; }
// Amb ternari (1 línia)
String r = (nota >= 5) ? "Aprovat" : "Suspès";El ternari és elegant per a casos senzills, però no l’aniuïs. Això és il·legible:
String x = a > b ? (a > c ? "a" : "c") : (b > c ? "b" : "c"); // difícil de llegirQuan la decisió té més de dos camins o inclou instruccions (no només un valor), fes servir if-else o switch. La claredat és més important que estalviar línies.
6.8 Quina estructura triar
flowchart TD
A{"Quantes<br/>opcions?"} -->|"1 (fer o no fer)"| B["if"]
A -->|"2 camins"| C{"Només assignes<br/>un valor?"}
C -->|Sí| D["operador ternari"]
C -->|No| E["if-else"]
A -->|"molts valors<br/>d'una variable"| F["switch (millor modern)"]
A -->|"rangs o<br/>condicions complexes"| G["cadena else if"]
Cap regla és sagrada: totes es poden reescriure amb if-else. Tria la que faci el codi més clar de llegir.
6.9 Resum
- Una estructura de selecció fa que el programa triï un camí segons una condició booleana.
ifexecuta un bloc només si la condició és certa;if-elsetria entre dos camins.- Les cadenes
else iftrien entre múltiples camins excloents; l’ordre de les condicions importa. - El
switchcompara una variable amb molts valors.- El clàssic necessita
break(i oblidar-lo causa fall-through); - El modern amb
->és més curt i segur, i pot retornar un valor.
- El clàssic necessita
- L’operador ternari
? :és una drecera per a decisions curtes que assignen un valor. - Els dos errors més freqüents: confondre
==(comparar) amb=(assignar), i oblidar elbreakalswitchclàssic.
6.10 Per practicar
- Classificador de notes. Demana una nota (0–10) i escriu la qualificació (Suspès, Aprovat, Notable, Excel·lent) amb una cadena
else if. - Calculadora simple. Demana dos nombres i una operació (
+,-,*,/) i fes servir unswitchmodern per calcular i mostrar el resultat. - Any de traspàs. Demana un any i digues si és de traspàs (divisible per 4, però no per 100 tret que ho sigui per 400). Practica els operadors lògics.
- Major de tres. Demana tres nombres i escriu el més gran. Fes-ho primer amb
if-elsei després intenta-ho amb ternaris. - Preu amb descompte. Demana un import; si supera 100 €, aplica un 10 % de descompte amb l’operador ternari i mostra el preu final.
- Menú de restaurant. Amb un
switchclàssic, mostra el preu d’un plat segons un codi numèric, i afegeix a propòsit un error debreakoblidat per veure què passa.