001package org.jsoup.select; 002 003import org.jsoup.nodes.Element; 004import org.jspecify.annotations.Nullable; 005 006import java.util.Optional; 007import java.util.stream.Collectors; 008 009/** 010 * Collects a list of elements that match the supplied criteria. 011 * 012 * @author Jonathan Hedley 013 */ 014public class Collector { 015 016 private Collector() {} 017 018 /** 019 Build a list of elements, by visiting root and every descendant of root, and testing it against the evaluator. 020 @param eval Evaluator to test elements against 021 @param root root of tree to descend 022 @return list of matches; empty if none 023 */ 024 public static Elements collect (Evaluator eval, Element root) { 025 eval.reset(); 026 027 return root.stream() 028 .filter(eval.asPredicate(root)) 029 .collect(Collectors.toCollection(Elements::new)); 030 } 031 032 /** 033 Finds the first Element that matches the Evaluator that descends from the root, and stops the query once that first 034 match is found. 035 @param eval Evaluator to test elements against 036 @param root root of tree to descend 037 @return the first match; {@code null} if none 038 */ 039 public static @Nullable Element findFirst(Evaluator eval, Element root) { 040 eval.reset(); 041 042 Optional<Element> first = root.stream().filter(eval.asPredicate(root)).findFirst(); 043 return first.orElse(null); 044 } 045}