Iterator.remove în Java

Șterge din colecție elementul returnat ultima dată de next(). Este felul sigur de a șterge în timpul parcurgerii.

Sintaxă
default void remove()

Iterator<E> it = set.iterator();

Ce face Iterator.remove

it.remove() șterge elementul pe care tocmai l-a dat it.next(). Spre deosebire de colectie.remove(x), nu strică parcurgerea: iteratorul știe de ștergere și continuă corect.

Se poate apela o singură dată după fiecare next(). Dacă îl apelezi înainte de primul next() sau de două ori la rând, apare IllegalStateException. Colecțiile nemodificabile (List.of, Set.of) aruncă UnsupportedOperationException.

Pagina acoperă și Set.iterator(): o mulțime nu are poziții, deci iteratorul este singura cale de a lua elementele unul câte unul (la TreeSet în ordine sortată, la HashSet într-o ordine nespecificată). Pentru cazurile simple, removeIf este mai scurt.

Ce returnează

Nimic (void).

Exemple

Exemplul 1: Ștergerea produselor expirate dintr-o mulțime

import java.util.Iterator;
import java.util.List;
import java.util.TreeSet;

public class Main {
    public static void main(String[] args) {
        TreeSet<String> produse = new TreeSet<>(List.of("iaurt-exp", "lapte", "brânză-exp", "unt"));
        Iterator<String> it = produse.iterator();
        while (it.hasNext()) {
            String p = it.next();
            if (p.endsWith("-exp")) {
                it.remove();
                System.out.println("Scos: " + p);
            }
        }
        System.out.println("Rămase: " + produse);
    }
}

Rezultat

Scos: brânză-exp
Scos: iaurt-exp
Rămase: [lapte, unt]

Exemplul 2: Greșit și corect: ștergerea în for-each

import java.util.ArrayList;
import java.util.ConcurrentModificationException;
import java.util.Iterator;
import java.util.List;

public class Main {
    public static void main(String[] args) {
        List<Integer> note = new ArrayList<>(List.of(4, 9, 3, 8));
        try {
            for (Integer n : note) {
                if (n < 5) {
                    note.remove(n);
                }
            }
        } catch (ConcurrentModificationException e) {
            System.out.println("for-each + remove: ConcurrentModificationException");
        }

        note = new ArrayList<>(List.of(4, 9, 3, 8));
        for (Iterator<Integer> it = note.iterator(); it.hasNext(); ) {
            if (it.next() < 5) {
                it.remove();
            }
        }
        System.out.println("Cu Iterator.remove: " + note);
    }
}

Rezultat

for-each + remove: ConcurrentModificationException
Cu Iterator.remove: [9, 8]

Exemplul 3: remove() fără next()

import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

public class Main {
    public static void main(String[] args) {
        Iterator<String> it = new ArrayList<>(List.of("Ana", "Radu")).iterator();
        try {
            it.remove();
        } catch (IllegalStateException e) {
            System.out.println("IllegalStateException: întâi trebuie apelat next()");
        }
    }
}

Rezultat

IllegalStateException: întâi trebuie apelat next()

Greșeli frecvente

  • Apelezi it.remove() de două ori după un singur next(). A doua oară apare IllegalStateException.
  • Ștergi cu colectie.remove(x) în loc de it.remove() în timpul parcurgerii. Apare ConcurrentModificationException.
  • Te bazezi pe ordinea iteratorului unui HashSet. Nu este garantată; folosește TreeSet sau LinkedHashSet dacă ordinea contează.

Comenzi înrudite

  • Iterator: Obiectul care parcurge o colecție element cu element: hasNext() întreabă dacă mai urmează ceva, next() îl dă pe următorul.
  • Collection.removeIf: Șterge din colecție toate elementele pentru care condiția dată este adevărată. Returnează true dacă s-a șters ceva.
  • List.iterator: iterator parcurge lista înainte; listIterator poate merge și înapoi, poate înlocui și insera elemente.
  • Set: Interfața pentru mulțimi: colecții fără duplicate, în care întrebi rapid dacă un element există.
  • TreeSet: Mulțime care ține elementele mereu sortate (crescător sau după un Comparator) și oferă căutări de tip „cel mai mic”, „cel mai apropiat”.