View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.lang3.stream;
18  
19  import java.util.ArrayList;
20  import java.util.Collection;
21  import java.util.Collections;
22  import java.util.Enumeration;
23  import java.util.Iterator;
24  import java.util.List;
25  import java.util.Objects;
26  import java.util.Set;
27  import java.util.Spliterator;
28  import java.util.Spliterators;
29  import java.util.Spliterators.AbstractSpliterator;
30  import java.util.function.BiConsumer;
31  import java.util.function.BinaryOperator;
32  import java.util.function.Consumer;
33  import java.util.function.Function;
34  import java.util.function.Predicate;
35  import java.util.function.Supplier;
36  import java.util.stream.Collector;
37  import java.util.stream.Collectors;
38  import java.util.stream.Stream;
39  import java.util.stream.StreamSupport;
40  
41  import org.apache.commons.lang3.ArrayUtils;
42  import org.apache.commons.lang3.function.Failable;
43  import org.apache.commons.lang3.function.FailableConsumer;
44  import org.apache.commons.lang3.function.FailableFunction;
45  import org.apache.commons.lang3.function.FailablePredicate;
46  
47  /**
48   * Provides utility functions, and classes for working with the {@link java.util.stream} package, or more generally, with Java 8 lambdas. More specifically, it
49   * attempts to address the fact that lambdas are supposed not to throw Exceptions, at least not checked Exceptions, AKA instances of {@link Exception}. This
50   * enforces the use of constructs like:
51   *
52   * <pre>{@code
53   * Consumer<java.lang.reflect.Method> consumer = m -> {
54   *     try {
55   *         m.invoke(o, args);
56   *     } catch (Throwable t) {
57   *         throw Failable.rethrow(t);
58   *     }
59   * };
60   * stream.forEach(consumer);
61   * }</pre>
62   * <p>
63   * Using a {@link FailableStream}, this can be rewritten as follows:
64   * </p>
65   *
66   * <pre>{@code
67   * Streams.failable(stream).forEach(m -> m.invoke(o, args));
68   * }</pre>
69   * <p>
70   * Obviously, the second version is much more concise and the spirit of Lambda expressions is met better than in the first version.
71   * </p>
72   *
73   * @see Stream
74   * @see Failable
75   * @since 3.11
76   */
77  public class Streams {
78  
79      /**
80       * A Collector type for arrays.
81       *
82       * @param <E> The array type.
83       */
84      public static class ArrayCollector<E> implements Collector<E, List<E>, E[]> {
85          private static final Set<Characteristics> characteristics = Collections.emptySet();
86          private final Class<E> elementType;
87  
88          /**
89           * Constructs a new instance for the given element type.
90           *
91           * @param elementType The element type.
92           */
93          public ArrayCollector(final Class<E> elementType) {
94              this.elementType = Objects.requireNonNull(elementType, "elementType");
95          }
96  
97          @Override
98          public BiConsumer<List<E>, E> accumulator() {
99              return List::add;
100         }
101 
102         @Override
103         public Set<Characteristics> characteristics() {
104             return characteristics;
105         }
106 
107         @Override
108         public BinaryOperator<List<E>> combiner() {
109             return (left, right) -> {
110                 left.addAll(right);
111                 return left;
112             };
113         }
114 
115         @Override
116         public Function<List<E>, E[]> finisher() {
117             return list -> list.toArray(ArrayUtils.newInstance(elementType, list.size()));
118         }
119 
120         @Override
121         public Supplier<List<E>> supplier() {
122             return ArrayList::new;
123         }
124     }
125 
126     /**
127      * Helps implement {@link Streams#of(Enumeration)}.
128      *
129      * @param <T> The element type.
130      */
131     private static final class EnumerationSpliterator<T> extends AbstractSpliterator<T> {
132 
133         private final Enumeration<T> enumeration;
134 
135         /**
136          * Creates a spliterator reporting the given estimated size and additionalCharacteristics.
137          *
138          * @param estimatedSize the estimated size of this spliterator if known, otherwise {@code Long.MAX_VALUE}.
139          * @param additionalCharacteristics properties of this spliterator's source or elements. If {@code SIZED} is reported then this spliterator will
140          *        additionally report {@code SUBSIZED}.
141          * @param enumeration The Enumeration to wrap.
142          */
143         protected EnumerationSpliterator(final long estimatedSize, final int additionalCharacteristics, final Enumeration<T> enumeration) {
144             super(estimatedSize, additionalCharacteristics);
145             this.enumeration = Objects.requireNonNull(enumeration, "enumeration");
146         }
147 
148         @Override
149         public void forEachRemaining(final Consumer<? super T> action) {
150             while (enumeration.hasMoreElements()) {
151                 next(action);
152             }
153         }
154 
155         private boolean next(final Consumer<? super T> action) {
156             action.accept(enumeration.nextElement());
157             return true;
158 
159         }
160 
161         @Override
162         public boolean tryAdvance(final Consumer<? super T> action) {
163             return enumeration.hasMoreElements() && next(action);
164         }
165     }
166 
167     /**
168      * A reduced, and simplified version of a {@link Stream} with failable method signatures.
169      *
170      * @param <T> The streams element type.
171      */
172     public static class FailableStream<T> {
173 
174         private Stream<T> stream;
175         private boolean terminated;
176 
177         /**
178          * Constructs a new instance with the given {@code stream}.
179          *
180          * @param stream The stream.
181          */
182         public FailableStream(final Stream<T> stream) {
183             this.stream = stream;
184         }
185 
186         /**
187          * Returns whether all elements of this stream match the provided predicate. May not evaluate the predicate on all
188          * elements if not necessary for determining the result. If the stream is empty then {@code true} is returned and the
189          * predicate is not evaluated.
190          *
191          * <p>
192          * This is a short-circuiting terminal operation.
193          * </p>
194          *
195          * Note This method evaluates the <em>universal quantification</em> of the predicate over the elements of the stream
196          * (for all x P(x)). If the stream is empty, the quantification is said to be <em>vacuously satisfied</em> and is always
197          * {@code true} (regardless of P(x)).
198          *
199          * @param predicate A non-interfering, stateless predicate to apply to elements of this stream
200          * @return {@code true} If either all elements of the stream match the provided predicate or the stream is empty,
201          *         otherwise {@code false}.
202          */
203         public boolean allMatch(final FailablePredicate<T, ?> predicate) {
204             assertNotTerminated();
205             return stream().allMatch(Failable.asPredicate(predicate));
206         }
207 
208         /**
209          * Returns whether any elements of this stream match the provided predicate. May not evaluate the predicate on all
210          * elements if not necessary for determining the result. If the stream is empty then {@code false} is returned and the
211          * predicate is not evaluated.
212          *
213          * <p>
214          * This is a short-circuiting terminal operation.
215          * </p>
216          *
217          * Note This method evaluates the <em>existential quantification</em> of the predicate over the elements of the stream
218          * (for some x P(x)).
219          *
220          * @param predicate A non-interfering, stateless predicate to apply to elements of this stream
221          * @return {@code true} if any elements of the stream match the provided predicate, otherwise {@code false}
222          */
223         public boolean anyMatch(final FailablePredicate<T, ?> predicate) {
224             assertNotTerminated();
225             return stream().anyMatch(Failable.asPredicate(predicate));
226         }
227 
228         /**
229          * Throws IllegalStateException if this stream is already terminated.
230          *
231          * @throws IllegalStateException if this stream is already terminated.
232          */
233         protected void assertNotTerminated() {
234             if (terminated) {
235                 throw new IllegalStateException("This stream is already terminated.");
236             }
237         }
238 
239         /**
240          * Performs a mutable reduction operation on the elements of this stream using a {@link Collector}. A {@link Collector}
241          * encapsulates the functions used as arguments to {@link #collect(Supplier, BiConsumer, BiConsumer)}, allowing for
242          * reuse of collection strategies and composition of collect operations such as multiple-level grouping or partitioning.
243          *
244          * <p>
245          * If the underlying stream is parallel, and the {@link Collector} is concurrent, and either the stream is unordered or
246          * the collector is unordered, then a concurrent reduction will be performed (see {@link Collector} for details on
247          * concurrent reduction.)
248          * </p>
249          *
250          * <p>
251          * This is a terminal operation.
252          * </p>
253          *
254          * <p>
255          * When executed in parallel, multiple intermediate results may be instantiated, populated, and merged so as to maintain
256          * isolation of mutable data structures. Therefore, even when executed in parallel with non-thread-safe data structures
257          * (such as {@link ArrayList}), no additional synchronization is needed for a parallel reduction.
258          * </p>
259          *
260          * Note The following will accumulate strings into an ArrayList:
261          *
262          * <pre>
263          * {@code
264          *     List<String> asList = stringStream.collect(Collectors.toList());
265          * }
266          * </pre>
267          *
268          * <p>
269          * The following will classify {@code Person} objects by city:
270          * </p>
271          *
272          * <pre>
273          * {@code
274          *     Map<String, List<Person>> peopleByCity = personStream.collect(Collectors.groupingBy(Person::getCity));
275          * }
276          * </pre>
277          *
278          * <p>
279          * The following will classify {@code Person} objects by state and city, cascading two {@link Collector}s together:
280          * </p>
281          *
282          * <pre>
283          * {@code
284          *     Map<String, Map<String, List<Person>>> peopleByStateAndCity = personStream
285          *         .collect(Collectors.groupingBy(Person::getState, Collectors.groupingBy(Person::getCity)));
286          * }
287          * </pre>
288          *
289          * @param <R> the type of the result
290          * @param <A> the intermediate accumulation type of the {@link Collector}
291          * @param collector the {@link Collector} describing the reduction
292          * @return the result of the reduction
293          * @see #collect(Supplier, BiConsumer, BiConsumer)
294          * @see Collectors
295          */
296         public <A, R> R collect(final Collector<? super T, A, R> collector) {
297             makeTerminated();
298             return stream().collect(collector);
299         }
300 
301         /**
302          * Performs a mutable reduction operation on the elements of this FailableStream. A mutable reduction is one in which
303          * the reduced value is a mutable result container, such as an {@link ArrayList}, and elements are incorporated by
304          * updating the state of the result rather than by replacing the result. This produces a result equivalent to:
305          * <pre>
306          * {@code
307          *     R result = supplier.get();
308          *     for (T element : this stream)
309          *         accumulator.accept(result, element);
310          *     return result;
311          * }
312          * </pre>
313          * <p>
314          * Like {@link #reduce(Object, BinaryOperator)}, {@code collect} operations can be parallelized without requiring
315          * additional synchronization.
316          * </p>
317          * <p>
318          * This is a terminal operation.
319          * </p>
320          * <p>
321          * Note There are many existing classes in the JDK whose signatures are well-suited for use with method references as
322          * arguments to {@code collect()}. For example, the following will accumulate strings into an {@link ArrayList}:
323          * </p>
324          * <pre>
325          * {@code
326          *     List<String> asList = stringStream.collect(ArrayList::new, ArrayList::add, ArrayList::addAll);
327          * }
328          * </pre>
329          * <p>
330          * The following will take a stream of strings and concatenates them into a single string:
331          * </p>
332          * <pre>
333          * {@code
334          *     String concat = stringStream.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append).toString();
335          * }
336          * </pre>
337          *
338          * @param <R> type of the result
339          * @param <A> Type of the accumulator.
340          * @param supplier a function that creates a new result container. For a parallel execution, this function may be called
341          *        multiple times and must return a fresh value each time.
342          * @param accumulator An associative, non-interfering, stateless function for incorporating an additional element into a
343          *        result
344          * @param combiner An associative, non-interfering, stateless function for combining two values, which must be
345          *        compatible with the accumulator function
346          * @return The result of the reduction
347          */
348         public <A, R> R collect(final Supplier<R> supplier, final BiConsumer<R, ? super T> accumulator, final BiConsumer<R, R> combiner) {
349             makeTerminated();
350             return stream().collect(supplier, accumulator, combiner);
351         }
352 
353         /**
354          * Returns a FailableStream consisting of the elements of this stream that match the given FailablePredicate.
355          * <p>
356          * This is an intermediate operation.
357          * </p>
358          *
359          * @param predicate a non-interfering, stateless predicate to apply to each element to determine if it should be
360          *        included.
361          * @return the new stream
362          */
363         public FailableStream<T> filter(final FailablePredicate<T, ?> predicate) {
364             assertNotTerminated();
365             stream = stream.filter(Failable.asPredicate(predicate));
366             return this;
367         }
368 
369         /**
370          * Performs an action for each element of this stream.
371          * <p>
372          * This is a terminal operation.
373          * </p>
374          * <p>
375          * The behavior of this operation is explicitly nondeterministic. For parallel stream pipelines, this operation does
376          * <em>not</em> guarantee to respect the encounter order of the stream, as doing so would sacrifice the benefit of
377          * parallelism. For any given element, the action may be performed at whatever time and in whatever thread the library
378          * chooses. If the action accesses shared state, it is responsible for providing the required synchronization.
379          * </p>
380          *
381          * @param action a non-interfering action to perform on the elements
382          */
383         public void forEach(final FailableConsumer<T, ?> action) {
384             makeTerminated();
385             stream().forEach(Failable.asConsumer(action));
386         }
387 
388         /**
389          * Marks this stream as terminated.
390          *
391          * @throws IllegalStateException if this stream is already terminated.
392          */
393         protected void makeTerminated() {
394             assertNotTerminated();
395             terminated = true;
396         }
397 
398         /**
399          * Returns a stream consisting of the results of applying the given function to the elements of this stream.
400          *
401          * <p>
402          * This is an intermediate operation.
403          * </p>
404          *
405          * @param <R> The element type of the new stream
406          * @param mapper A non-interfering, stateless function to apply to each element
407          * @return the new stream
408          */
409         public <R> FailableStream<R> map(final FailableFunction<T, R, ?> mapper) {
410             assertNotTerminated();
411             return new FailableStream<>(stream.map(Failable.asFunction(mapper)));
412         }
413 
414         /**
415          * Performs a reduction on the elements of this stream, using the provided identity value and an associative
416          * accumulation function, and returns the reduced value. This is equivalent to:
417          *
418          * <pre>
419          * {@code
420          *     T result = identity;
421          *     for (T element : this stream)
422          *         result = accumulator.apply(result, element)
423          *     return result;
424          * }
425          * </pre>
426          *
427          * but is not constrained to execute sequentially.
428          *
429          * <p>
430          * The {@code identity} value must be an identity for the accumulator function. This means that for all {@code t},
431          * {@code accumulator.apply(identity, t)} is equal to {@code t}. The {@code accumulator} function must be an associative
432          * function.
433          * </p>
434          *
435          * <p>
436          * This is a terminal operation.
437          * </p>
438          *
439          * Note Sum, min, max, average, and string concatenation are all special cases of reduction. Summing a stream of numbers
440          * can be expressed as:
441          *
442          * <pre>
443          * {@code
444          *     Integer sum = integers.reduce(0, (a, b) -> a + b);
445          * }
446          * </pre>
447          *
448          * or:
449          *
450          * <pre>
451          * {@code
452          *     Integer sum = integers.reduce(0, Integer::sum);
453          * }
454          * </pre>
455          *
456          * <p>
457          * While this may seem a more roundabout way to perform an aggregation compared to simply mutating a running total in a
458          * loop, reduction operations parallelize more gracefully, without needing additional synchronization and with greatly
459          * reduced risk of data races.
460          * </p>
461          *
462          * @param identity the identity value for the accumulating function
463          * @param accumulator an associative, non-interfering, stateless function for combining two values
464          * @return the result of the reduction
465          */
466         public T reduce(final T identity, final BinaryOperator<T> accumulator) {
467             makeTerminated();
468             return stream().reduce(identity, accumulator);
469         }
470 
471         /**
472          * Converts the FailableStream into an equivalent stream.
473          *
474          * @return A stream, which will return the same elements, which this FailableStream would return.
475          */
476         public Stream<T> stream() {
477             return stream;
478         }
479     }
480 
481     /**
482      * Converts the given {@link Collection} into a {@link FailableStream}. This is basically a simplified, reduced version
483      * of the {@link Stream} class, with the same underlying element stream, except that failable objects, like
484      * {@link FailablePredicate}, {@link FailableFunction}, or {@link FailableConsumer} may be applied, instead of
485      * {@link Predicate}, {@link Function}, or {@link Consumer}. The idea is to rewrite a code snippet like this:
486      *
487      * <pre>
488      * {@code
489      * final List<O> list;
490      * final Method m;
491      * final Function<O, String> mapper = (o) -> {
492      *     try {
493      *         return (String) m.invoke(o);
494      *     } catch (Throwable t) {
495      *         throw Failable.rethrow(t);
496      *     }
497      * };
498      * final List<String> strList = list.stream().map(mapper).collect(Collectors.toList());
499      * }
500      * </pre>
501      *
502      * as follows:
503      *
504      * <pre>
505      * {@code
506      * final List<O> list;
507      * final Method m;
508      * final List<String> strList = Failable.stream(list.stream()).map((o) -> (String) m.invoke(o)).collect(Collectors.toList());
509      * }
510      * </pre>
511      *
512      * While the second version may not be <em>quite</em> as efficient (because it depends on the creation of additional,
513      * intermediate objects, of type FailableStream), it is much more concise, and readable, and meets the spirit of Lambdas
514      * better than the first version.
515      *
516      * @param <T> The streams element type.
517      * @param stream The stream, which is being converted.
518      * @return The {@link FailableStream}, which has been created by converting the stream.
519      * @since 3.13.0
520      */
521     public static <T> FailableStream<T> failableStream(final Collection<T> stream) {
522         return failableStream(of(stream));
523     }
524 
525     /**
526      * Converts the given {@link Stream stream} into a {@link FailableStream}. This is basically a simplified, reduced
527      * version of the {@link Stream} class, with the same underlying element stream, except that failable objects, like
528      * {@link FailablePredicate}, {@link FailableFunction}, or {@link FailableConsumer} may be applied, instead of
529      * {@link Predicate}, {@link Function}, or {@link Consumer}. The idea is to rewrite a code snippet like this:
530      *
531      * <pre>
532      * {@code
533      * final List<O> list;
534      * final Method m;
535      * final Function<O, String> mapper = (o) -> {
536      *     try {
537      *         return (String) m.invoke(o);
538      *     } catch (Throwable t) {
539      *         throw Failable.rethrow(t);
540      *     }
541      * };
542      * final List<String> strList = list.stream().map(mapper).collect(Collectors.toList());
543      * }
544      * </pre>
545      *
546      * as follows:
547      *
548      * <pre>
549      * {@code
550      * final List<O> list;
551      * final Method m;
552      * final List<String> strList = Failable.stream(list.stream()).map((o) -> (String) m.invoke(o)).collect(Collectors.toList());
553      * }
554      * </pre>
555      *
556      * While the second version may not be <em>quite</em> as efficient (because it depends on the creation of additional,
557      * intermediate objects, of type FailableStream), it is much more concise, and readable, and meets the spirit of Lambdas
558      * better than the first version.
559      *
560      * @param <T> The streams element type.
561      * @param stream The stream, which is being converted.
562      * @return The {@link FailableStream}, which has been created by converting the stream.
563      * @since 3.13.0
564      */
565     public static <T> FailableStream<T> failableStream(final Stream<T> stream) {
566         return new FailableStream<>(stream);
567     }
568 
569     /**
570      * Shorthand for {@code Streams.failableStream(value == null ? Stream.empty() : Stream.of(value))}.
571      *
572      * @param <T> the type of stream elements.
573      * @param value the single element of the new stream, may be {@code null}.
574      * @return the new FailableStream on {@code value} or an empty stream.
575      * @since 3.15.0
576      */
577     public static <T> FailableStream<T> failableStream(final T value) {
578         return failableStream(streamOf(value));
579     }
580 
581     /**
582      * Shorthand for {@code Streams.failableStream(Streams.of(arrayValues))}.
583      *
584      * @param <T> the type of stream elements.
585      * @param values the elements of the new stream, may be {@code null}.
586      * @return the new FailableStream on {@code values} or an empty stream.
587      * @since 3.14.0
588      */
589     @SafeVarargs // Creating a stream from an array is safe
590     public static <T> FailableStream<T> failableStream(final T... values) {
591         return failableStream(of(values));
592     }
593 
594     /**
595      * Streams only instances of the give Class in a collection.
596      * <p>
597      * This method shorthand for:
598      * </p>
599      * <pre>
600      * {@code (Stream<E>) Streams.toStream(collection).filter(collection, SomeClass.class::isInstance);}
601      * </pre>
602      *
603      * @param <E> the type of elements in the collection we want to stream.
604      * @param clazz the type of elements in the collection we want to stream.
605      * @param collection the collection to stream or null.
606      * @return A non-null stream that only provides instances we want.
607      * @since 3.13.0
608      */
609     public static <E> Stream<E> instancesOf(final Class<? super E> clazz, final Collection<? super E> collection) {
610         return instancesOf(clazz, of(collection));
611     }
612 
613     @SuppressWarnings("unchecked") // After the isInstance check, we still need to type-cast.
614     private static <E> Stream<E> instancesOf(final Class<? super E> clazz, final Stream<?> stream) {
615         return (Stream<E>) of(stream).filter(clazz::isInstance);
616     }
617 
618     /**
619      * Streams the non-null elements of a collection.
620      *
621      * @param <E> the type of elements in the collection.
622      * @param collection the collection to stream or null.
623      * @return A non-null stream that filters out null elements.
624      * @since 3.13.0
625      */
626     public static <E> Stream<E> nonNull(final Collection<E> collection) {
627         return of(collection).filter(Objects::nonNull);
628     }
629 
630     /**
631      * Streams the non-null element.
632      *
633      * @param <E> the type of elements in the collection.
634      * @param array the element to stream or null.
635      * @return A non-null stream that filters out a null element.
636      * @since 3.15.0
637      */
638     public static <E> Stream<E> nonNull(final E array) {
639         return nonNull(streamOf(array));
640     }
641 
642     /**
643      * Streams the non-null elements of an array.
644      *
645      * @param <E> the type of elements in the collection.
646      * @param array the array to stream or null.
647      * @return A non-null stream that filters out null elements.
648      * @since 3.13.0
649      */
650     @SafeVarargs
651     public static <E> Stream<E> nonNull(final E... array) {
652         return nonNull(of(array));
653     }
654 
655     /**
656      * Streams the non-null elements of a stream.
657      *
658      * @param <E> the type of elements in the collection.
659      * @param stream the stream to stream or null.
660      * @return A non-null stream that filters out null elements.
661      * @since 3.13.0
662      */
663     public static <E> Stream<E> nonNull(final Stream<E> stream) {
664         return of(stream).filter(Objects::nonNull);
665     }
666 
667     /**
668      * Delegates to {@link Collection#stream()} or returns {@link Stream#empty()} if the collection is null.
669      *
670      * @param <E> the type of elements in the collection.
671      * @param collection the collection to stream or null.
672      * @return {@link Collection#stream()} or {@link Stream#empty()} if the collection is null.
673      * @since 3.13.0
674      */
675     public static <E> Stream<E> of(final Collection<E> collection) {
676         return collection == null ? Stream.empty() : collection.stream();
677     }
678 
679     /**
680      * Streams the elements of the given enumeration in order.
681      *
682      * @param <E> The enumeration element type.
683      * @param enumeration The enumeration to stream.
684      * @return a new stream.
685      * @since 3.13.0
686      */
687     public static <E> Stream<E> of(final Enumeration<E> enumeration) {
688         return StreamSupport.stream(new EnumerationSpliterator<>(Long.MAX_VALUE, Spliterator.ORDERED, enumeration), false);
689     }
690 
691     /**
692      * Creates a stream on the given Iterable.
693      *
694      * @param <E> the type of elements in the Iterable.
695      * @param iterable the Iterable to stream or null.
696      * @return a new Stream or {@link Stream#empty()} if the Iterable is null.
697      * @since 3.13.0
698      */
699     public static <E> Stream<E> of(final Iterable<E> iterable) {
700         return iterable == null ? Stream.empty() : StreamSupport.stream(iterable.spliterator(), false);
701     }
702 
703     /**
704      * Creates a stream on the given Iterator.
705      *
706      * @param <E> the type of elements in the Iterator.
707      * @param iterator the Iterator to stream or null.
708      * @return a new Stream or {@link Stream#empty()} if the Iterator is null.
709      * @since 3.13.0
710      */
711     public static <E> Stream<E> of(final Iterator<E> iterator) {
712         return iterator == null ? Stream.empty() : StreamSupport.stream(Spliterators.spliteratorUnknownSize(iterator, Spliterator.ORDERED), false);
713     }
714 
715     /**
716      * Returns the stream or {@link Stream#empty()} if the stream is null.
717      *
718      * @param <E> the type of elements in the collection.
719      * @param stream the stream to stream or null.
720      * @return the stream or {@link Stream#empty()} if the stream is null.
721      * @since 3.13.0
722      */
723     private static <E> Stream<E> of(final Stream<E> stream) {
724         return stream == null ? Stream.empty() : stream;
725     }
726 
727     /**
728      * Null-safe version of {@link Stream#of(Object[])}.
729      *
730      * @param <T> the type of stream elements.
731      * @param values the elements of the new stream, may be {@code null}.
732      * @return the new stream on {@code values} or {@link Stream#empty()}.
733      * @since 3.13.0
734      */
735     @SafeVarargs // Creating a stream from an array is safe
736     public static <T> Stream<T> of(final T... values) {
737         return values == null ? Stream.empty() : Stream.of(values);
738     }
739 
740     /**
741      * Converts the given {@link Collection} into a {@link FailableStream}. This is basically a simplified, reduced version
742      * of the {@link Stream} class, with the same underlying element stream, except that failable objects, like
743      * {@link FailablePredicate}, {@link FailableFunction}, or {@link FailableConsumer} may be applied, instead of
744      * {@link Predicate}, {@link Function}, or {@link Consumer}. The idea is to rewrite a code snippet like this:
745      *
746      * <pre>
747      * {@code
748      * final List<O> list;
749      * final Method m;
750      * final Function<O, String> mapper = (o) -> {
751      *     try {
752      *         return (String) m.invoke(o);
753      *     } catch (Throwable t) {
754      *         throw Failable.rethrow(t);
755      *     }
756      * };
757      * final List<String> strList = list.stream().map(mapper).collect(Collectors.toList());
758      * }
759      * </pre>
760      *
761      * as follows:
762      *
763      * <pre>
764      * {@code
765      * final List<O> list;
766      * final Method m;
767      * final List<String> strList = Failable.stream(list.stream()).map((o) -> (String) m.invoke(o)).collect(Collectors.toList());
768      * }
769      * </pre>
770      *
771      * While the second version may not be <em>quite</em> as efficient (because it depends on the creation of additional,
772      * intermediate objects, of type FailableStream), it is much more concise, and readable, and meets the spirit of Lambdas
773      * better than the first version.
774      *
775      * @param <E> The streams element type.
776      * @param collection The stream, which is being converted.
777      * @return The {@link FailableStream}, which has been created by converting the stream.
778      * @deprecated Use {@link #failableStream(Collection)}.
779      */
780     @Deprecated
781     public static <E> FailableStream<E> stream(final Collection<E> collection) {
782         return failableStream(collection);
783     }
784 
785     /**
786      * Converts the given {@link Stream stream} into a {@link FailableStream}. This is basically a simplified, reduced
787      * version of the {@link Stream} class, with the same underlying element stream, except that failable objects, like
788      * {@link FailablePredicate}, {@link FailableFunction}, or {@link FailableConsumer} may be applied, instead of
789      * {@link Predicate}, {@link Function}, or {@link Consumer}. The idea is to rewrite a code snippet like this:
790      *
791      * <pre>
792      * {@code
793      * final List<O> list;
794      * final Method m;
795      * final Function<O, String> mapper = (o) -> {
796      *     try {
797      *         return (String) m.invoke(o);
798      *     } catch (Throwable t) {
799      *         throw Failable.rethrow(t);
800      *     }
801      * };
802      * final List<String> strList = list.stream().map(mapper).collect(Collectors.toList());
803      * }
804      * </pre>
805      *
806      * as follows:
807      *
808      * <pre>
809      * {@code
810      * final List<O> list;
811      * final Method m;
812      * final List<String> strList = Failable.stream(list.stream()).map((o) -> (String) m.invoke(o)).collect(Collectors.toList());
813      * }
814      * </pre>
815      *
816      * While the second version may not be <em>quite</em> as efficient (because it depends on the creation of additional,
817      * intermediate objects, of type FailableStream), it is much more concise, and readable, and meets the spirit of Lambdas
818      * better than the first version.
819      *
820      * @param <T> The streams element type.
821      * @param stream The stream, which is being converted.
822      * @return The {@link FailableStream}, which has been created by converting the stream.
823      * @deprecated Use {@link #failableStream(Stream)}.
824      */
825     @Deprecated
826     public static <T> FailableStream<T> stream(final Stream<T> stream) {
827         return failableStream(stream);
828     }
829 
830     private static <T> Stream<T> streamOf(final T value) {
831         return value == null ? Stream.empty() : Stream.of(value);
832     }
833 
834     /**
835      * Returns a {@link Collector} that accumulates the input elements into a new array.
836      *
837      * @param elementType Type of an element in the array.
838      * @param <T> the type of the input elements
839      * @return a {@link Collector} which collects all the input elements into an array, in encounter order
840      */
841     public static <T> Collector<T, ?, T[]> toArray(final Class<T> elementType) {
842         return new ArrayCollector<>(elementType);
843     }
844 
845     /**
846      * Constructs a new instance.
847      *
848      * @deprecated Will be private in 4.0.0.
849      */
850     @Deprecated
851     public Streams() {
852         // empty
853     }
854 }