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

public final class Main {

    public static void main(String[] args) {
        Predicate<String> p = s -> s.startsWith("b");
        findFirst(p);
        limitList(p);
    }

    public static void findFirst(Predicate<String> matchesFavorite) {
        var firstFavorite = List.of("foo", "bar", "baz")
            .stream()
            .filter(matchesFavorite)
            .findFirst();
        firstFavorite.ifPresent(s -> System.out.println("A:" + s));

        // As a result, it is equivalent to the following code:
        List.of("foo", "bar", "baz")
            .stream()
            .filter(matchesFavorite)
            .findFirst()
            .ifPresent(s -> System.out.println("B:" + s));
    }

    public static void limitList(Predicate<String> matchesFavorite) {
        var favoriteList = List.of("foo", "bar", "baz")
            .stream()
            .filter(matchesFavorite)
            .limit(1)
            .collect(Collectors.toList());

        favoriteList.forEach(s -> System.out.println("C:" + s));

        // Or
        for (var s : favoriteList) {
            // This loop only runs once at most.
            System.out.println("D:" + s);
        }

        // Or again, it could be as follows, but...
        if (favoriteList.size() != 0) {
            var s = favoriteList.get(0);
            System.out.println("E:" + s);
        }

        // As a result, it is equivalent to the following code:
        List.of("foo", "bar", "baz")
            .stream()
            .filter(matchesFavorite)
            .limit(1)
            .forEach(s -> System.out.println("F:" + s));
    }
}
