CodeGym /Corsi /SQL SELF /Interrompere e continuare i cicli: EXIT, CONTINUE

Interrompere e continuare i cicli: EXIT, CONTINUE

SQL SELF
Livello 51 , Lezione 2
Disponibile

A volte in un ciclo tutto fila liscio... finché non spunta un motivo per fermarsi prima. Per fortuna, PL/pgSQL ci dà strumenti comodi per gestire questa cosa.

Interrompere un ciclo con EXIT

Capita che bisogna terminare un ciclo prima che finisca da solo. Magari perché hai trovato il valore che cercavi, hai beccato un errore o hai raggiunto una certa condizione. In questi casi usiamo EXIT.

EXIT è il modo per "dire" al ciclo: "Basta così, hai fatto il tuo, ora stop".

La sintassi di EXIT è super semplice:

EXIT WHEN condizione;

Qui la parola chiave WHEN indica quando il ciclo deve essere interrotto. Se non metti la condizione, EXIT chiude subito il ciclo corrente.

Esempio: terminare il ciclo quando trovi il valore giusto

Supponiamo di avere una colonna con i numeri degli studenti e vogliamo trovare lo studente con un certo ID. Appena lo troviamo, il ciclo deve finire.

DO $$
DECLARE
    student_id INT;
BEGIN
    FOR student_id IN 1..100 LOOP
        RAISE NOTICE 'Sto controllando lo studente ID: %', student_id;

        -- Se troviamo lo studente giusto, chiudiamo il ciclo
        IF student_id = 42 THEN
            RAISE NOTICE 'Studente con ID 42 trovato!';
            EXIT;
        END IF;
    END LOOP;
END $$;

In questo esempio il ciclo scorre i numeri da 1 a 100, controllando ogni "studente". Appena trova l'ID 42, stampa il messaggio e termina il ciclo.

Saltare un'iterazione con CONTINUE

Capita che dentro un ciclo vuoi saltare certe iterazioni, ma continuare con la prossima. È utile se vuoi ignorare dati "inutili" o saltare passi per condizioni particolari.

CONTINUE dice: "Ok, questa condizione non ci va bene, passiamo direttamente alla prossima iterazione".

CONTINUE funziona come EXIT, solo che invece di chiudere il ciclo, salta l'iterazione corrente:

CONTINUE WHEN condizione;

Se la condizione è vera, l'iterazione attuale si chiude e si passa subito alla prossima.

Esempio: saltare i numeri pari

In questo esempio scorriamo i numeri da 1 a 10, ma ignoriamo quelli pari e stampiamo solo i dispari.

DO $$
DECLARE
    num INT;
BEGIN
    FOR num IN 1..10 LOOP
        -- Saltiamo i numeri pari
        IF num % 2 = 0 THEN
            CONTINUE;
        END IF;

        RAISE NOTICE 'Numero dispari: %', num;
    END LOOP;
END $$;

Qui CONTINUE salta tutte le iterazioni dove num % 2 = 0 (cioè il numero è pari). Quindi nel log vedrai solo i numeri dispari.

Combinare EXIT e CONTINUE

EXIT e CONTINUE si possono usare insieme per gestire il ciclo in modo più flessibile. Per esempio, puoi saltare le iterazioni inutili con CONTINUE, ma chiudere tutto il ciclo se trovi qualcosa di importante.

Ecco un esempio dove saltiamo tutti i numeri multipli di 3, ma chiudiamo il ciclo appena arriviamo al numero 15.

DO $$
DECLARE
    num INT;
BEGIN
    FOR num IN 1..20 LOOP
        -- Saltiamo i numeri multipli di 3
        IF num % 3 = 0 THEN
            CONTINUE;
        END IF;

        -- Chiudiamo il ciclo se il numero è 15
        IF num = 15 THEN
            RAISE NOTICE 'Mi fermo al numero %', num;
            EXIT;
        END IF;

        RAISE NOTICE 'Numero attuale: %', num;
    END LOOP;
END $$;

Qui il ciclo funziona così:

  • I numeri multipli di 3 vengono saltati (CONTINUE).
  • Se il numero è 15, il ciclo si ferma (EXIT).
  • Tutti gli altri numeri vengono stampati.

Esempio avanzato: saltare dati non validi e fermarsi su errore critico

Ora immaginiamo un caso più reale. Vogliamo processare una lista di studenti, controllando i loro dati. Le registrazioni non valide le saltiamo, ma in caso di "errore critico" fermiamo tutto.

DO $$
DECLARE
    student RECORD;
BEGIN
    FOR student IN
        SELECT * FROM students
    LOOP
        -- Saltiamo le registrazioni con dati non validi
        IF student.name IS NULL THEN
            RAISE NOTICE 'Salto lo studente con ID %: Nome mancante', student.id;
            CONTINUE;
        END IF;

        -- Fermiamo il ciclo su errore critico
        IF student.status = 'ERRORE' THEN
            RAISE EXCEPTION 'Errore critico per lo studente ID %', student.id;
            EXIT; -- Questa riga in realtà è superflua, perché RAISE EXCEPTION ferma tutto.
        END IF;

        -- Elaborazione della registrazione
        RAISE NOTICE 'Sto processando lo studente: %', student.name;
    END LOOP;
END $$;

In questo esempio CONTINUE serve per saltare gli studenti senza nome, mentre EXIT (insieme a RAISE EXCEPTION) ferma tutto se c'è un errore serio.

Consigli pratici ed errori tipici

Non dimenticare la logica delle condizioni. Usare male le condizioni dentro EXIT WHEN o CONTINUE WHEN può portare a comportamenti strani. Tipo che il ciclo si ferma troppo presto o salta dati importanti.

Non esagerare con CONTINUE. Se il tuo codice è pieno di controlli con CONTINUE, forse è il caso di rivedere la logica del ciclo per semplificarla.

Non confondere EXIT e RETURN. EXIT chiude solo il ciclo corrente, mentre RETURN termina tutta la funzione.

Occhio ai cicli infiniti. Se usi un ciclo LOOP senza una condizione chiara di uscita, ti dimentichi di EXIT e il ciclo va avanti all'infinito.

Commenti
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION