1868 * Returns a {@code Collector} which applies an {@code double}-producing 1869 * mapping function to each input element, and returns summary statistics 1870 * for the resulting values. 1871 * 1872 * @param <T> the type of the input elements 1873 * @param mapper a mapping function to apply to each element 1874 * @return a {@code Collector} implementing the summary-statistics reduction 1875 * 1876 * @see #summarizingLong(ToLongFunction) 1877 * @see #summarizingInt(ToIntFunction) 1878 */ 1879 public static <T> 1880 Collector<T, ?, DoubleSummaryStatistics> summarizingDouble(ToDoubleFunction<? super T> mapper) { 1881 return new CollectorImpl<T, DoubleSummaryStatistics, DoubleSummaryStatistics>( 1882 DoubleSummaryStatistics::new, 1883 (r, t) -> r.accept(mapper.applyAsDouble(t)), 1884 (l, r) -> { l.combine(r); return l; }, CH_ID); 1885 } 1886 1887 /** 1888 * Implementation class used by partitioningBy. 1889 */ 1890 private static final class Partition<T> 1891 extends AbstractMap<Boolean, T> 1892 implements Map<Boolean, T> { 1893 final T forTrue; 1894 final T forFalse; 1895 1896 Partition(T forTrue, T forFalse) { 1897 this.forTrue = forTrue; 1898 this.forFalse = forFalse; 1899 } 1900 1901 @Override 1902 public Set<Map.Entry<Boolean, T>> entrySet() { 1903 return new AbstractSet<>() { 1904 @Override 1905 public Iterator<Map.Entry<Boolean, T>> iterator() { 1906 Map.Entry<Boolean, T> falseEntry = new SimpleImmutableEntry<>(false, forFalse); 1907 Map.Entry<Boolean, T> trueEntry = new SimpleImmutableEntry<>(true, forTrue); | 1868 * Returns a {@code Collector} which applies an {@code double}-producing 1869 * mapping function to each input element, and returns summary statistics 1870 * for the resulting values. 1871 * 1872 * @param <T> the type of the input elements 1873 * @param mapper a mapping function to apply to each element 1874 * @return a {@code Collector} implementing the summary-statistics reduction 1875 * 1876 * @see #summarizingLong(ToLongFunction) 1877 * @see #summarizingInt(ToIntFunction) 1878 */ 1879 public static <T> 1880 Collector<T, ?, DoubleSummaryStatistics> summarizingDouble(ToDoubleFunction<? super T> mapper) { 1881 return new CollectorImpl<T, DoubleSummaryStatistics, DoubleSummaryStatistics>( 1882 DoubleSummaryStatistics::new, 1883 (r, t) -> r.accept(mapper.applyAsDouble(t)), 1884 (l, r) -> { l.combine(r); return l; }, CH_ID); 1885 } 1886 1887 /** 1888 * Returns a {@code Collector} which aggregates the results of two supplied 1889 * collectors using the supplied finisher function. 1890 * 1891 * <p>The resulting collector is {@link Collector.Characteristics#UNORDERED} if both supplied 1892 * collectors are unordered and {@link Collector.Characteristics#CONCURRENT} if both supplied 1893 * collectors are concurrent. 1894 * 1895 * @param <T> the type of the input elements 1896 * @param <R1> the result type of the first collector 1897 * @param <R2> the result type of the second collector 1898 * @param <R> the final result type 1899 * @param c1 the first collector 1900 * @param c2 the second collector 1901 * @param finisher the function which merges two results into the single one 1902 * @return a {@code Collector} which aggregates the results of two supplied collectors. 1903 */ 1904 public static <T, R1, R2, R> 1905 Collector<T, ?, R> pairing(Collector<? super T, ?, R1> c1, 1906 Collector<? super T, ?, R2> c2, 1907 BiFunction<? super R1, ? super R2, ? extends R> finisher) { 1908 return pairing0(c1, c2, finisher); 1909 } 1910 1911 private static <T, A1, A2, R1, R2, R> 1912 Collector<T, ?, R> pairing0(Collector<? super T, A1, R1> c1, 1913 Collector<? super T, A2, R2> c2, 1914 BiFunction<? super R1, ? super R2, ? extends R> finisher) { 1915 Objects.requireNonNull(c1, "c1"); 1916 Objects.requireNonNull(c2, "c2"); 1917 Objects.requireNonNull(finisher, "finisher"); 1918 EnumSet<Collector.Characteristics> c = EnumSet.noneOf(Collector.Characteristics.class); 1919 c.addAll(c1.characteristics()); 1920 c.retainAll(c2.characteristics()); 1921 c.remove(Collector.Characteristics.IDENTITY_FINISH); 1922 1923 Supplier<A1> c1Supplier = Objects.requireNonNull(c1.supplier(), "c1 supplier"); 1924 Supplier<A2> c2Supplier = Objects.requireNonNull(c2.supplier(), "c2 supplier"); 1925 BiConsumer<A1, ? super T> c1Accumulator = Objects.requireNonNull(c1.accumulator(), "c1 accumulator"); 1926 BiConsumer<A2, ? super T> c2Accumulator = Objects.requireNonNull(c2.accumulator(), "c2 accumulator"); 1927 BinaryOperator<A1> c1Combiner = Objects.requireNonNull(c1.combiner(), "c1 combiner"); 1928 BinaryOperator<A2> c2Combiner = Objects.requireNonNull(c2.combiner(), "c2 combiner"); 1929 Function<A1, R1> c1Finisher = Objects.requireNonNull(c1.finisher(), "c1 finisher"); 1930 Function<A2, R2> c2Finisher = Objects.requireNonNull(c2.finisher(), "c2 finisher"); 1931 1932 class PairBox { 1933 A1 left = c1Supplier.get(); 1934 A2 right = c2Supplier.get(); 1935 1936 void add(T t) { 1937 c1Accumulator.accept(left, t); 1938 c2Accumulator.accept(right, t); 1939 } 1940 1941 PairBox combine(PairBox other) { 1942 left = c1Combiner.apply(left, other.left); 1943 right = c2Combiner.apply(right, other.right); 1944 return this; 1945 } 1946 1947 R get() { 1948 R1 r1 = c1Finisher.apply(left); 1949 R2 r2 = c2Finisher.apply(right); 1950 return finisher.apply(r1, r2); 1951 } 1952 } 1953 1954 return new CollectorImpl<>(PairBox::new, PairBox::add, PairBox::combine, PairBox::get, 1955 Collections.unmodifiableSet(c)); 1956 } 1957 1958 /** 1959 * Implementation class used by partitioningBy. 1960 */ 1961 private static final class Partition<T> 1962 extends AbstractMap<Boolean, T> 1963 implements Map<Boolean, T> { 1964 final T forTrue; 1965 final T forFalse; 1966 1967 Partition(T forTrue, T forFalse) { 1968 this.forTrue = forTrue; 1969 this.forFalse = forFalse; 1970 } 1971 1972 @Override 1973 public Set<Map.Entry<Boolean, T>> entrySet() { 1974 return new AbstractSet<>() { 1975 @Override 1976 public Iterator<Map.Entry<Boolean, T>> iterator() { 1977 Map.Entry<Boolean, T> falseEntry = new SimpleImmutableEntry<>(false, forFalse); 1978 Map.Entry<Boolean, T> trueEntry = new SimpleImmutableEntry<>(true, forTrue); |