Predicate.and în Java

Combină condiții: and (ambele adevărate), or (cel puțin una) și negate (condiția inversă).

Sintaxă
default Predicate<T> and(Predicate<? super T> altul)
default Predicate<T> or(Predicate<? super T> altul)
default Predicate<T> negate()

Ce face Predicate.and

p.and(q) creează un predicat adevărat doar când p și q sunt adevărate, ca &&. p.or(q) este adevărat când cel puțin unul este adevărat, ca ||. Ambele se opresc devreme: dacă p decide deja rezultatul, q nu mai rulează.

p.negate() inversează rezultatul, ca !. Așa construiești filtre complexe din bucăți mici, cu nume clare, pe care le poți refolosi.

Parametri

Parametru Descriere
altul Al doilea predicat.

Ce returnează

Un Predicate nou, combinat.

Exemple

Exemplul 1: Filtre pentru apartamente

import java.util.List;
import java.util.function.Predicate;

public class Main {
    record Apartament(String oras, int camere, int pret) {}

    public static void main(String[] args) {
        List<Apartament> anunturi = List.of(
                new Apartament("Iași", 2, 85_000), new Apartament("Iași", 3, 120_000),
                new Apartament("Cluj", 2, 140_000), new Apartament("Iași", 1, 55_000));

        Predicate<Apartament> inIasi = a -> a.oras().equals("Iași");
        Predicate<Apartament> ieftin = a -> a.pret() < 100_000;
        Predicate<Apartament> mare = a -> a.camere() >= 3;

        System.out.println("Iași și ieftin: " + anunturi.stream().filter(inIasi.and(ieftin)).toList());
        System.out.println("Ieftin sau mare: " + anunturi.stream().filter(ieftin.or(mare)).count());
        System.out.println("În afara Iașului: " + anunturi.stream().filter(inIasi.negate()).toList());
    }
}

Rezultat

Iași și ieftin: [Apartament[oras=Iași, camere=2, pret=85000], Apartament[oras=Iași, camere=1, pret=55000]]
Ieftin sau mare: 3
În afara Iașului: [Apartament[oras=Cluj, camere=2, pret=140000]]

Exemplul 2: Validarea unei parole din reguli mici

Fiecare regulă are numele ei; regula finală este combinația lor.

import java.util.function.Predicate;

public class Main {
    public static void main(String[] args) {
        Predicate<String> lunga = s -> s.length() >= 8;
        Predicate<String> areCifra = s -> s.chars().anyMatch(Character::isDigit);
        Predicate<String> areSpatiu = s -> s.contains(" ");

        Predicate<String> buna = lunga.and(areCifra).and(areSpatiu.negate());

        for (String parola : new String[]{"soare", "soare2026", "soare 2026"}) {
            System.out.println(parola + " -> " + buna.test(parola));
        }
    }
}

Rezultat

soare -> false
soare2026 -> true
soare 2026 -> false

Greșeli frecvente

  • Combini predicate de tipuri diferite (Predicate<String> cu Predicate<Integer>): nu compilează.
  • Uiți că and/or returnează un predicat nou. p.and(q); singur nu schimbă p.

Comenzi înrudite

  • Predicate: O condiție: primește o valoare și răspunde true sau false prin metoda test; folosită de filter, removeIf, anyMatch.
  • Predicate.not: Inversează o condiție dată ca referință de metodă: filter(Predicate.not(String::isBlank)) păstrează textele care nu sunt goale.
  • Stream.filter: Păstrează în stream doar elementele care îndeplinesc o condiție.
  • Function.andThen: Leagă două funcții una după alta: f.andThen(g) rulează întâi f, apoi g; f.compose(g) rulează întâi g, apoi f.