-
- 型パラメータ:
T
- ストリーム要素の型
- すべてのスーパー・インタフェース:
AutoCloseable
,BaseStream<T,Stream<T>>
public interface Stream<T> extends BaseStream<T,Stream<T>>
順次および並列の集約操作をサポートする要素のシーケンスです。 次の例は、Stream
とIntStream
を使用する集計操作を示したものです。
この例では、int sum = widgets.stream() .filter(w -> w.getColor() == RED) .mapToInt(w -> w.getWeight()) .sum();
widgets
はCollection<Widget>
です。Collection.stream()
経由でWidget
オブジェクトのストリームが作成され、その結果がフィルタリングされて赤色のウィジェットのみを含むストリームが生成された後、それが、各赤色ウィジェットの重量を表すint
値のストリームに変換されます。 続いてこのストリームが合計され、合計重量が生成されます。オブジェクト参照のストリームである
Stream
のほかに、IntStream
、LongStream
およびDoubleStream
用のプリミティブ特殊化も存在しており、これらもすべてストリームと呼ばれ、ここで記述する特性や制限に準拠します。計算を実行できるように、複数のストリーム操作を組み合わせて1つのストリーム・パイプラインが形成されます。 ストリーム・パイプラインは、1つのソース(配列、コレクション、ジェネレータ関数、入出力チャネルなど)、0個以上の中間操作(
filter(Predicate)
など、あるストリームを別のストリームに変換する操作)および1つの終端操作(count()
やforEach(Consumer)
など、結果または副作用を生成する操作)から構成されます。 ストリームは遅延処理されます。ソース・データに対する計算は終端操作が起動されるまで実行されず、ソース要素も必要なだけしか消費されません。ストリームの実装には、結果の計算を最適化する際に重要な緯度が許可されます。 例えば、ストリームの実装はストリーム・パイプラインから(または全ステージ)オペレーションを削除することが自由です-- したがって、行動パラメータの呼び出しを無効にします-- それが計算の結果に影響しないことが証明できれば。 これは、行動パラメータの副作用が必ずしも実行されるとは限らないことを意味し、特に指定されない限り、依存するべきではないことを意味します。(端末操作
forEach
およびforEachOrdered
などによる)。 (このような最適化の具体例については、count()
操作で説明されているAPIノートを参照してください。 詳細については、ストリーム・パッケージのドキュメントのside-effectsセクションを参照してください。)コレクションとストリームは、表面上似た点があるものの、異なる目的を持っています。 コレクションは主に、要素の効率的な管理やアクセスに注力しています。 これに対し、ストリームは要素の直接アクセスや操作の手段を持たず、代わりにソースやそのソースに対して集約的に実行される計算操作を宣言的に記述することに注力しています。 ただし、用意されたストリーム操作が必要な機能を提供しない場合には、
BaseStream.iterator()
およびBaseStream.spliterator()
操作を使って制御されたトラバーサルを実行することもできます。ストリーム・パイプラインは、上の「widgets」の例のように、ストリーム・ソースに対する問合せとみなすことができます。 ソースが明示的に同時変更向けに設計されたもの(
ConcurrentHashMap
など)でないかぎり、ストリームのソースを照会中に変更すると、予測不可能な動作や間違った動作が発生する可能性があります。ほとんどのストリーム操作は、上の例で
mapToInt
に渡されたラムダ式w -> w.getWeight()
のような、ユーザー指定の動作を記述するパラメータを受け取ります。 正しい動作を維持するには、これらの動作パラメータは次を満たす必要があります。- 非干渉でなければいけない(ストリームのソースを変更しない)、および
- ほとんどの場合、ステートレスでなければいけない(その結果は、ストリーム・パイプラインの実行中に変化する可能性のあるどの状態にも依存すべきでない)。
そのようなパラメータは常に関数型インタフェース(
Function
など)のインスタンスであり、通常はラムダ式やメソッド参照になります。 特に明記されていないかぎり、これらのパラメータはnull以外でなければいけません。(中間または終端ストリーム操作を呼び出して)ストリームを操作するのは、一度だけにすべきです。 このため、たとえば同じソースが2つ以上のパイプラインに対してデータを供給する「フォークされた」ストリームや、同じストリームを複数回トラバースすることなどは、禁止されます。 ストリーム実装は、ストリームが再利用されているのを検出すると、
IllegalStateException
をスローします。 ただし、一部のストリーム操作からは新しいストリーム・オブジェクトではなくレシーバが返されることがあるため、場合によっては再利用を検出できない可能性があります。ストリームは
BaseStream.close()
メソッドを持ち、AutoCloseable
を実装します。 ストリームが閉じられた後でストリームを操作すると、IllegalStateException
がスローされます。 ほとんどのストリーム・インスタンスは、特別なリソース管理を必要としないコレクション、配列、または生成関数によってサポートされているため、実際には使用後に閉じる必要はありません。 一般的に、Files.lines(Path)
によって返されるものなど、IOチャネルであるストリームを持つストリームのみがクローズする必要があります。 ストリームが終了する必要がある場合は、try-with-resources文または同様の制御構造内のリソースとしてオープンして、操作が完了した後すぐに閉じられるようにする必要があります。ストリーム・パイプラインは順次、並列のいずれかで実行できます。 この実行モードは、ストリームのプロパティの1つです。 ストリームの作成時には、順次実行または並列実行の初期選択が行われます。 (たとえば、
Collection.stream()
では順次ストリームが作成され、Collection.parallelStream()
では並列ストリームが作成されます。) この実行モードの選択を変更するにはBaseStream.sequential()
またはBaseStream.parallel()
メソッドを使用し、実行モードを照会するにはBaseStream.isParallel()
メソッドを使用します。- 導入されたバージョン:
- 1.8
- 関連項目:
IntStream
,LongStream
,DoubleStream
, java.util.stream
-
-
ネストされたクラスのサマリー
ネストされたクラス 修飾子と型 インタフェース 説明 static interface
Stream.Builder<T>
Stream
の可変ビルダーです。
-
メソッドのサマリー
すべてのメソッド staticメソッド インスタンス・メソッド 抽象メソッド デフォルト・メソッド 修飾子と型 メソッド 説明 boolean
allMatch(Predicate<? super T> predicate)
このストリームのすべての要素が指定された述語に一致するかどうかを返します。boolean
anyMatch(Predicate<? super T> predicate)
このストリームのいずれかの要素が指定された述語に一致するかどうかを返します。static <T> Stream.Builder<T>
builder()
Stream
のビルダーを返します。<R> R
collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
このストリームの要素に対して可変リダクション操作を実行します。<R,A>
Rcollect(Collector<? super T,A,R> collector)
Collector
を使ってこのストリームの要素に対する可変リダクション操作を実行します。static <T> Stream<T>
concat(Stream<? extends T> a, Stream<? extends T> b)
最初のストリームの全要素と2番目のストリームの全要素を連結したものを要素に持つ、遅延連結ストリームを作成します。long
count()
このストリームの要素の個数を返します。Stream<T>
distinct()
このストリームの重複を除いた要素(Object.equals(Object)
による)から構成されるストリームを返します。default Stream<T>
dropWhile(Predicate<? super T> predicate)
このストリームが順序付けされている場合は、指定された述語に一致する要素の最長プレフィクスを削除した後に、このストリームの残りの要素で構成されるストリームを返します。static <T> Stream<T>
empty()
空の順次Stream
を返します。Stream<T>
filter(Predicate<? super T> predicate)
このストリームの要素のうち、指定された述語に一致するものから構成されるストリームを返します。Optional<T>
findAny()
ストリームの一部の要素を記述するOptional
を返します。ストリームが空の場合は空のOptional
を返します。Optional<T>
findFirst()
このストリームの最初の要素を記述するOptional
を返します。ストリームが空の場合は空のOptional
を返します。<R> Stream<R>
flatMap(Function<? super T,? extends Stream<? extends R>> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るストリームを返します。DoubleStream
flatMapToDouble(Function<? super T,? extends DoubleStream> mapper)
このストリームの各要素を、その要素に指定されたマッピング関数を適用することによって生成されるマップ先ストリームの内容で置き換えた結果から構成されるDoubleStream
を返します。IntStream
flatMapToInt(Function<? super T,? extends IntStream> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るIntStream
を返します。LongStream
flatMapToLong(Function<? super T,? extends LongStream> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るLongStream
を返します。void
forEach(Consumer<? super T> action)
このストリームの各要素に対してアクションを実行します。void
forEachOrdered(Consumer<? super T> action)
このストリームの各要素に対してアクションを実行します。その実行順は、ストリームの検出順が定義されている場合はその順番になります。static <T> Stream<T>
generate(Supplier<? extends T> s)
指定されたSupplier
によって生成される要素を含む、順序付けされていない無限順次ストリームを返します。static <T> Stream<T>
iterate(T seed, Predicate<? super T> hasNext, UnaryOperator<T> next)
指定されたnext
関数を初期要素に反復適用することによって生成され、与えられたhasNext
述語を満たすことを条件とする、順次順序付けされたStream
を返します。static <T> Stream<T>
iterate(T seed, UnaryOperator<T> f)
初期要素seed
に関数f
を繰り返し適用することで生成される、順序付けされた無限順次Stream
を返します(seed
、f(seed)
、f(f(seed))
、といった要素から成るStream
が生成される)。Stream<T>
limit(long maxSize)
このストリームの要素をmaxSize
以内の長さに切り詰めた結果から成るストリームを返します。<R> Stream<R>
map(Function<? super T,? extends R> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるストリームを返します。DoubleStream
mapToDouble(ToDoubleFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるDoubleStream
を返します。IntStream
mapToInt(ToIntFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるIntStream
を返します。LongStream
mapToLong(ToLongFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるLongStream
を返します。Optional<T>
max(Comparator<? super T> comparator)
指定されたComparator
に従ってこのストリームの最大要素を返します。Optional<T>
min(Comparator<? super T> comparator)
指定されたComparator
に従ってこのストリームの最小要素を返します。boolean
noneMatch(Predicate<? super T> predicate)
指定された述語に一致する要素がこのストリーム内に存在しないかどうかを返します。static <T> Stream<T>
of(T t)
単一要素を含む順次Stream
を返します。static <T> Stream<T>
of(T... values)
指定された値を要素に持つ、順序付けされた順次ストリームを返します。static <T> Stream<T>
ofNullable(T t)
非nullならば、単一の要素を含むシーケンシャルなStream
を返します。それ以外の場合は空のStream
を返します。Stream<T>
peek(Consumer<? super T> action)
このストリームの要素から成るストリームを返すほか、その結果のストリームから消費される各要素に対し、指定されたアクションを実行します。Optional<T>
reduce(BinaryOperator<T> accumulator)
T
reduce(T identity, BinaryOperator<T> accumulator)
<U> U
reduce(U identity, BiFunction<U,? super T,U> accumulator, BinaryOperator<U> combiner)
指定された単位元、累積関数、および結合的関数を使用して、このストリームの要素に対してリダクションを実行します。Stream<T>
skip(long n)
このストリームの最初のn
個の要素を破棄した残りの要素で構成されるストリームを返します。Stream<T>
sorted()
このストリームの要素を自然順序に従ってソートした結果から構成されるストリームを返します。Stream<T>
sorted(Comparator<? super T> comparator)
このストリームの要素を指定されたComparator
に従ってソートした結果から構成されるストリームを返します。default Stream<T>
takeWhile(Predicate<? super T> predicate)
このストリームが順序付けされている場合、指定された述語に一致するこのストリームから取得された要素の最長プレフィクスからなるストリームを返します。Object[]
toArray()
このストリームの要素を含む配列を返します。<A> A[]
toArray(IntFunction<A[]> generator)
指定されたgenerator
関数を使用して、このストリームの要素を含む配列を返し、返された配列と、パーティション化された実行またはサイズ変更に必要となる可能性のある追加の配列を割り当てます。-
インタフェース java.util.stream.BaseStreamで宣言されたメソッド
close, isParallel, iterator, onClose, parallel, sequential, spliterator, unordered
-
-
-
-
メソッドの詳細
-
filter
Stream<T> filter(Predicate<? super T> predicate)
このストリームの要素のうち、指定された述語に一致するものから構成されるストリームを返します。これは中間操作です。
-
map
<R> Stream<R> map(Function<? super T,? extends R> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるストリームを返します。これは中間操作です。
-
mapToInt
IntStream mapToInt(ToIntFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるIntStream
を返します。これは中間操作です。
-
mapToLong
LongStream mapToLong(ToLongFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるLongStream
を返します。これは中間操作です。
-
mapToDouble
DoubleStream mapToDouble(ToDoubleFunction<? super T> mapper)
このストリームの要素に指定された関数を適用した結果から構成されるDoubleStream
を返します。これは中間操作です。
-
flatMap
<R> Stream<R> flatMap(Function<? super T,? extends Stream<? extends R>> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るストリームを返します。 各マップ先ストリームは、その内容がこのストリーム内に配置されるとクローズ
されます。 (マップ先ストリームがnull
の場合はかわりに空のストリームが使用されます。)これは中間操作です。
- APIのノート:
flatMap()
操作には、ストリームの要素に対して1対多の変換を適用した後、結果の要素を新しいストリーム内にフラット化する効果があります。例
orders
が購入注文のストリームであり、各購入注文には明細行のコレクションが含まれている場合、次のようにすると、すべての注文のすべての明細行を含むストリームが生成されます。orders.flatMap(order -> order.getLineItems().stream())...
path
がファイルへのパスである場合、次のようにすると、そのファイルに含まれる単語
のストリームが生成されます。Stream<String> lines = Files.lines(path, StandardCharsets.UTF_8); Stream<String> words = lines.flatMap(line -> Stream.of(line.split(" +")));
flatMap
に渡されたmapper
関数は、単純な正規表現を使って1行を単語の配列に分割した後、その配列から単語のストリームを作成します。- 型パラメータ:
R
- 新しいストリームの要素の型- パラメータ:
mapper
- 新しい値のストリームを生成するために各要素に適用する、非干渉でステートレスな関数- 戻り値:
- 新しいストリーム
-
flatMapToInt
IntStream flatMapToInt(Function<? super T,? extends IntStream> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るIntStream
を返します。 各マップ先ストリームは、その内容がこのストリーム内に配置されるとクローズ
されます。 (マップ先ストリームがnull
の場合はかわりに空のストリームが使用されます。)これは中間操作です。
- パラメータ:
mapper
- 新しい値のストリームを生成するために各要素に適用する、非干渉でステートレスな関数- 戻り値:
- 新しいストリーム
- 関連項目:
flatMap(Function)
-
flatMapToLong
LongStream flatMapToLong(Function<? super T,? extends LongStream> mapper)
このストリームの各要素をマップされたストリーム(指定されたマッピング関数を各要素に適用することで得られる)の内容で置き換えた結果から成るLongStream
を返します。 各マップ先ストリームは、その内容がこのストリーム内に配置されるとクローズ
されます。 (マップ先ストリームがnull
の場合はかわりに空のストリームが使用されます。)これは中間操作です。
- パラメータ:
mapper
- 新しい値のストリームを生成するために各要素に適用する、非干渉でステートレスな関数- 戻り値:
- 新しいストリーム
- 関連項目:
flatMap(Function)
-
flatMapToDouble
DoubleStream flatMapToDouble(Function<? super T,? extends DoubleStream> mapper)
このストリームの各要素を、その要素に指定されたマッピング関数を適用することによって生成されるマップ先ストリームの内容で置き換えた結果から構成されるDoubleStream
を返します。 各マップ先ストリームは、その内容がこのストリーム内に配置されるとクローズ
されます。 (マップ先ストリームがnull
の場合はかわりに空のストリームが使用されます。)これは中間操作です。
- パラメータ:
mapper
- 新しい値のストリームを生成するために各要素に適用する、非干渉でステートレスな関数- 戻り値:
- 新しいストリーム
- 関連項目:
flatMap(Function)
-
distinct
Stream<T> distinct()
このストリームの重複を除いた要素(Object.equals(Object)
による)から構成されるストリームを返します。順序付けされたストリームの場合、重複のない要素の選択は安定しています(重複した要素では、検出順で最初に現れた要素が維持されます。) 順序付けされていないストリームの場合、安定性は一切保証されません。
これはステートフルな中間操作です。
- APIのノート:
- 並列パイプラインで
distinct()
の安定性を維持するコストは比較的高くなります(操作が完全なバリアーとして動作する必要があり、バッファリングのオーバーヘッドがかなり大きくなる)が、安定性が不要なこともよくあります。 状況のセマンティックスが許せば、順序付けされていないストリーム・ソース(generate(Supplier)
など)を使用するか、BaseStream.unordered()
で順序付けの制約をなくせば、並列パイプラインでのdistinct()
の実行効率が大幅に向上する可能性があります。 検出順序との整合性が必要で、かつ並列パイプラインでのdistinct()
のパフォーマンスやメモリー使用量に問題がある場合には、BaseStream.sequential()
で順次実行に切り替えるとパフォーマンスが改善される可能性があります。 - 戻り値:
- 新しいストリーム
-
sorted
Stream<T> sorted()
このストリームの要素を自然順序に従ってソートした結果から構成されるストリームを返します。 このストリームの要素がComparable
でない場合は、終端操作の実行時にjava.lang.ClassCastException
がスローされる可能性があります。順序付けされたストリームの場合、ソートは安定しています。 順序付けされていないストリームの場合、安定性は一切保証されません。
これはステートフルな中間操作です。
- 戻り値:
- 新しいストリーム
-
sorted
Stream<T> sorted(Comparator<? super T> comparator)
このストリームの要素を指定されたComparator
に従ってソートした結果から構成されるストリームを返します。順序付けされたストリームの場合、ソートは安定しています。 順序付けされていないストリームの場合、安定性は一切保証されません。
これはステートフルな中間操作です。
-
peek
Stream<T> peek(Consumer<? super T> action)
このストリームの要素から成るストリームを返すほか、その結果のストリームから消費される各要素に対し、指定されたアクションを実行します。これは中間操作です。
並列ストリーム・パイプラインの場合、上流の操作によって用意された各要素に対し、任意のタイミングで任意のスレッド内でアクションが呼び出される可能性があります。 アクションが共有状態を変更する場合、必要な同期を提供する責任はアクションにあります。
- APIのノート:
- このメソッドの主な存在理由は、要素がパイプライン内の特定のポイントを通過する際にその内容を確認するようなデバッグをサポートすることにあります。
Stream.of("one", "two", "three", "four") .filter(e -> e.length() > 3) .peek(e -> System.out.println("Filtered value: " + e)) .map(String::toUpperCase) .peek(e -> System.out.println("Mapped value: " + e)) .collect(Collectors.toList());
ストリーム実装が要素(
findFirst
のような短絡操作やcount()
に記載されている例)の一部またはすべての生成を最適化できる場合、その要素に対してアクションは呼び出されません。 - パラメータ:
action
- ストリームから消費される要素に対して実行すべき非干渉アクション- 戻り値:
- 新しいストリーム
-
limit
Stream<T> limit(long maxSize)
このストリームの要素をmaxSize
以内の長さに切り詰めた結果から成るストリームを返します。これは、ステートフルな短絡中間操作です。
- APIのノート:
limit()
は、順次ストリーム・パイプラインでは一般に低コストの操作ですが、順序付けされた並列パイプラインではコストが非常に高くなる可能性があります(特にmaxSize
の値が大きい場合)。任意のn個の要素を返すだけでなく、検出順での最初のn個の要素を返さなければいけない、という制約がlimit(n)
に課されるからです。 状況のセマンティックスが許せば、順序付けされていないストリーム・ソース(generate(Supplier)
など)を使用するか、BaseStream.unordered()
で順序付けの制約をなくせば、並列パイプラインのlimit()
が大幅に高速化される可能性があります。 検出順序との整合性が必要で、かつ並列パイプラインでのlimit()
のパフォーマンスやメモリー使用量に問題がある場合には、BaseStream.sequential()
で順次実行に切り替えるとパフォーマンスが改善される可能性があります。- パラメータ:
maxSize
- ストリームの要素数の上限- 戻り値:
- 新しいストリーム
- 例外:
IllegalArgumentException
-maxSize
が負の場合
-
skip
Stream<T> skip(long n)
このストリームの最初のn
個の要素を破棄した残りの要素で構成されるストリームを返します。 このストリームに含まれる要素の数がn
個より少ない場合は、空のストリームが返されます。これはステートフルな中間操作です。
- APIのノート:
skip()
は、順次ストリーム・パイプラインでは一般に低コストの操作ですが、順序付けされた並列パイプラインではコストが非常に高くなる可能性があります(特にn
の値が大きい場合)。任意のn個の要素をスキップするだけでなく、検出順での最初のn個の要素をスキップしなければいけない、という制約がskip(n)
に課されるからです。 状況のセマンティックスが許せば、順序付けされていないストリーム・ソース(generate(Supplier)
など)を使用するか、BaseStream.unordered()
で順序付けの制約をなくせば、並列パイプラインのskip()
が大幅に高速化される可能性があります。 検出順序との整合性が必要で、かつ並列パイプラインでのskip()
のパフォーマンスやメモリー使用量に問題がある場合には、BaseStream.sequential()
で順次実行に切り替えるとパフォーマンスが改善される可能性があります。- パラメータ:
n
- スキップする先頭要素の数- 戻り値:
- 新しいストリーム
- 例外:
IllegalArgumentException
-n
が負の場合
-
takeWhile
default Stream<T> takeWhile(Predicate<? super T> predicate)
このストリームが順序付けされている場合、指定された述語に一致するこのストリームから取得された要素の最長プレフィクスからなるストリームを返します。 そうでない場合は、このストリームが順序付けられていない場合、指定された述語に一致するこのストリームから取り出された要素のサブセットからなるストリームを返します。このストリームが順序付けされている場合、最長のプレフィクスは、指定された述語に一致するこのストリームの要素の連続したシーケンスです。 シーケンスの最初の要素はこのストリームの最初の要素であり、シーケンスの最後の要素の直後の要素は指定された述語と一致しません。
このストリームが順序付けされておらず、このストリームの一部の(すべてではない)要素が指定された述語と一致する場合、この操作の動作は非決定的です。一致する要素(空のセットを含む)のサブセットを自由に取ることができます。
このストリームのすべての要素が指定された述語に一致する場合、このストリームが順序付けられているかどうかにかかわらず、この操作ではすべての要素(結果は入力と同じです)が使用され、ストリームの要素が指定された述語に一致しない場合は(結果は空のストリームです)は使用されません。
これは、ステートフルな短絡中間操作です。
- APIのノート:
takeWhile()
は通常、シーケンシャル・ストリーム・パイプラインでは安価な操作ですが、順序付けされたパラレル・パイプラインでは非常に高価ですが、操作は有効なプレフィクスだけでなく、エンカウンタの順序で要素の最長プレフィクスを返すように制限されています。 並べ替えられていないストリーム・ソース(generate(Supplier)
など)を使用するか、BaseStream.unordered()
で順序付け制約を削除すると、状況のセマンティクスが許せば、並列パイプラインでtakeWhile()
が大幅に高速化される可能性があります。 エンカウンタ・オーダーとの一貫性が必要で、並列パイプラインでtakeWhile()
のパフォーマンスやメモリー使用率が低下している場合は、BaseStream.sequential()
を使用して順次実行に切り替えるとパフォーマンスが向上する可能性があります。- 実装要件:
- デフォルトの実装では、このストリームの
spliterator
を取得し、そのスプライテータをラップしてこの操作のセマンティクスをトラバースでサポートし、ラップされたスプライテータに関連付けられた新しいストリームを返します。 返されたストリームはこのストリーム(BaseStream.isParallel()
による並列実行または順次実行)の実行特性を保持しますが、ラップされたスプライテータは分割をサポートしないことを選択することがあります。 返されたストリームが閉じられると、返されたストリームとこのストリームのクローズ・ハンドラが呼び出されます。 - パラメータ:
predicate
- non-interfering、stateless述語は、要素の最長プレフィクスを決定する要素に適用されます。- 戻り値:
- 新しいストリーム
- 導入されたバージョン:
- 9
-
dropWhile
default Stream<T> dropWhile(Predicate<? super T> predicate)
このストリームが順序付けされている場合は、指定された述語に一致する要素の最長プレフィクスを削除した後に、このストリームの残りの要素で構成されるストリームを返します。 そうでない場合は、このストリームが順序付けられていない場合は、指定された述語に一致する要素のサブセットを削除した後、このストリームの残りの要素からなるストリームを返します。このストリームが順序付けされている場合、最長のプレフィクスは、指定された述語に一致するこのストリームの要素の連続したシーケンスです。 シーケンスの最初の要素はこのストリームの最初の要素であり、シーケンスの最後の要素の直後の要素は指定された述語と一致しません。
このストリームが順序付けされておらず、このストリームの一部の(すべてではない)要素が指定された述語と一致する場合、この操作の動作は非決定的です。一致する要素(空のセットを含む)のサブセットを自由に削除することができます。
このストリームのすべての要素が指定された述語と一致する場合、このストリームが順序付けされているかどうかに関係なく、この操作ではすべての要素(結果は空のストリームです)が削除されるか、またはストリームの要素が指定された述語に一致しない場合、要素は削除されません(結果は入力と同じです)。
これはステートフルな中間操作です。
- APIのノート:
dropWhile()
は通常、シーケンシャル・ストリーム・パイプラインでは安価な操作ですが、順序付けされたパラレル・パイプラインでは非常に高価ですが、操作は有効なプレフィクスだけでなく、エンカウンタの順序で要素の最長プレフィクスを返すように制限されています。 並べ替えられていないストリーム・ソース(generate(Supplier)
など)を使用するか、BaseStream.unordered()
で順序付け制約を削除すると、状況のセマンティクスが許せば、並列パイプラインでdropWhile()
が大幅に高速化される可能性があります。 エンカウンタ・オーダーとの一貫性が必要で、並列パイプラインでdropWhile()
のパフォーマンスやメモリー使用率が低下している場合は、BaseStream.sequential()
を使用して順次実行に切り替えるとパフォーマンスが向上する可能性があります。- 実装要件:
- デフォルトの実装では、このストリームの
spliterator
を取得し、そのスプライテータをラップしてこの操作のセマンティクスをトラバースでサポートし、ラップされたスプライテータに関連付けられた新しいストリームを返します。 返されたストリームはこのストリーム(BaseStream.isParallel()
による並列実行または順次実行)の実行特性を保持しますが、ラップされたスプライテータは分割をサポートしないことを選択することがあります。 返されたストリームが閉じられると、返されたストリームとこのストリームのクローズ・ハンドラが呼び出されます。 - パラメータ:
predicate
- non-interfering、stateless述語は、要素の最長プレフィクスを決定する要素に適用されます。- 戻り値:
- 新しいストリーム
- 導入されたバージョン:
- 9
-
forEach
void forEach(Consumer<? super T> action)
このストリームの各要素に対してアクションを実行します。これは終端操作です。
この操作の動作は明らかに非決定論的です。 並列ストリーム・パイプラインの場合、この操作は、ストリームの検出順序を考慮することを保証しません。保証すると並列性のメリットが犠牲になるからです。 与えられた任意の要素に対し、ライブラリが選択した任意のタイミングで任意のスレッド内でアクションが実行される可能性があります。 アクションが共有状態にアクセスする場合、必要な同期を提供する責任はアクションにあります。
- パラメータ:
action
- 要素に対して実行する非干渉アクション
-
forEachOrdered
void forEachOrdered(Consumer<? super T> action)
このストリームの各要素に対してアクションを実行します。その実行順は、ストリームの検出順が定義されている場合はその順番になります。これは終端操作です。
この操作は、検出順序が存在する場合はその順序で、要素を一度に1つずつ処理します。 ある要素のアクション実行はその後続要素のアクション実行よりも前に発生しますが、どの要素についても、ライブラリが選択した任意のスレッド内でアクションが実行される可能性があります。
- パラメータ:
action
- 要素に対して実行する非干渉アクション- 関連項目:
forEach(Consumer)
-
toArray
Object[] toArray()
このストリームの要素を含む配列を返します。これは終端操作です。
- 戻り値:
- 「ランタイム・コンポーネント・タイプ」が
Object
の配列。このストリームの要素を含む
-
toArray
<A> A[] toArray(IntFunction<A[]> generator)
指定されたgenerator
関数を使用して、このストリームの要素を含む配列を返し、返された配列と、パーティション化された実行またはサイズ変更に必要となる可能性のある追加の配列を割り当てます。これは終端操作です。
- APIのノート:
- ジェネレータ関数は、要求された配列のサイズを表す整数を受け取り、要求されたサイズの配列を生成します。 これは、配列コンストラクタ参照で簡潔に表現できます。
Person[] men = people.stream() .filter(p -> p.getGender() == MALE) .toArray(Person[]::new);
- 型パラメータ:
A
- 結果の配列のコンポーネント型- パラメータ:
generator
- 要求された型と指定された長さを持つ新しい配列を生成する関数- 戻り値:
- このストリームの要素を含む配列
- 例外:
ArrayStoreException
- このストリームの要素の実行時の型が、生成された配列の「ランタイム・コンポーネント・タイプ」に代入可能でない場合
-
reduce
T reduce(T identity, BinaryOperator<T> accumulator)
指定された単位元の値と結合的な累積関数を使ってこのストリームの要素に対してリダクションを実行し、リデュースされた値を返します。 これは、次の操作に相当します。
ただし、順次実行の制約が課されるわけではありません。T result = identity; for (T element : this stream) result = accumulator.apply(result, element) return result;
identity
値はアキュムレータ関数の単位元でなければいけません。 つまり、すべてのt
について、accumulator.apply(identity, t)
がt
に等しくなります。アキュムレータ
関数は結合的な関数でなければいけません。これは終端操作です。
- APIのノート:
- 合計、最小、最大、平均、文字列連結はすべて、リダクションの特殊な場合です。 数値ストリームの合計は次のように表現できます。
またはInteger sum = integers.reduce(0, (a, b) -> a+b);
Integer sum = integers.reduce(0, Integer::sum);
これは、単純にループで中間合計を更新していく方法に比べて遠回りな集計方法に見えるかもしれませんが、リダクション操作の並列化が容易に行え、並列化の際に同期を追加する必要がなく、データ競合のリスクも大幅に減少します。
- パラメータ:
identity
- 蓄積関数に対する単位元の値accumulator
- 2つの値を結合するための結合的、非干渉、およびステートレスな関数- 戻り値:
- リダクションの結果
-
reduce
Optional<T> reduce(BinaryOperator<T> accumulator)
結合的な累積関数を使ってこのストリームの要素に対してリダクションを実行し、リデュースされた値が存在する場合はその値を記述するOptional
を返します。 これは、次の操作に相当します。
ただし、順次実行の制約が課されるわけではありません。boolean foundAny = false; T result = null; for (T element : this stream) { if (!foundAny) { foundAny = true; result = element; } else result = accumulator.apply(result, element); } return foundAny ? Optional.of(result) : Optional.empty();
アキュムレータ
関数は結合的な関数でなければいけません。これは終端操作です。
- パラメータ:
accumulator
- 2つの値を結合するための結合的、非干渉、およびステートレスな関数- 戻り値:
- リダクションの結果を記述する
Optional
- 例外:
NullPointerException
- リダクションの結果がnullの場合- 関連項目:
reduce(Object, BinaryOperator)
,min(Comparator)
,max(Comparator)
-
reduce
<U> U reduce(U identity, BiFunction<U,? super T,U> accumulator, BinaryOperator<U> combiner)
指定された単位元、累積関数、および結合的関数を使用して、このストリームの要素に対してリダクションを実行します。 これは、次の操作に相当します。
ただし、順次実行の制約が課されるわけではありません。U result = identity; for (T element : this stream) result = accumulator.apply(result, element) return result;
identity
値はコンバイナ関数の単位元でなければいけません。 つまり、すべてのu
について、combiner(identity, u)
がu
に等しくなります。 さらに、combiner
関数はaccumulator
関数と互換性がある必要があります。すべてのu
とt
について、次が成り立つ必要があります。combiner.apply(u, accumulator.apply(identity, t)) == accumulator.apply(u, t)
これは終端操作です。
- APIのノート:
- この形式を使用するリダクションの多くは、
map
操作とreduce
操作を明示的に組み合わせることで、より単純に表現することができます。accumulator
関数はマッパーとアキュムレータを融合したものとして動作しますが、これは、以前のリデュース値がわかっていれば一部の計算を回避できる場合など、マッピングとリダクションを個別に実行するよりも効率的になる場合があります。 - 型パラメータ:
U
- 結果の型- パラメータ:
identity
- コンバイナ関数に対する単位元の値accumulator
- 追加の要素を結果に組み込むための、結合的、非干渉およびステートレスな関数combiner
- 2つの値を結合するための結合的、非干渉およびステートレスな関数(アキュムレータ関数と互換性がなければいけない)- 戻り値:
- リダクションの結果
- 関連項目:
reduce(BinaryOperator)
,reduce(Object, BinaryOperator)
-
collect
<R> R collect(Supplier<R> supplier, BiConsumer<R,? super T> accumulator, BiConsumer<R,R> combiner)
このストリームの要素に対して可変リダクション操作を実行します。 可変リダクションとは、リデュース対象の値がArrayList
のような可変の結果コンテナであり、結果を置き換えるかわりに結果の状態を更新することによって要素が組み込まれるようなリダクションのことです。 これは次と同等の結果を生成します。R result = supplier.get(); for (T element : this stream) accumulator.accept(result, element); return result;
collect
操作はreduce(Object, BinaryOperator)
と同様、同期を追加しなくても並列化できます。これは終端操作です。
- APIのノート:
- JDKには、
collect()
の引数(メソッド参照)での使用に適したシグネチャを持つ既存クラスが多数存在しています。 たとえば次の場合、文字列がArrayList
内に蓄積されます。List<String> asList = stringStream.collect(ArrayList::new, ArrayList::add, ArrayList::addAll);
次の場合、文字列のストリームが受け取られ、それらが連結されて単一の文字列になります。
String concat = stringStream.collect(StringBuilder::new, StringBuilder::append, StringBuilder::append) .toString();
- 型パラメータ:
R
- 可変結果コンテナの型- パラメータ:
supplier
- 新しい変更可能な結果コンテナを作成する関数。 並列実行の場合、この関数は複数回呼び出される可能性がありますが、そのたびに新しい値を返す必要があります。accumulator
- associative、non-interfering、stateless関数は、要素を結果コンテナに折りたたむ必要があります。combiner
- associative、non-interfering、stateless関数は、2つの部分結果コンテナを受け入れ、それらをマージします。これらのコンテナは、アキュムレータ関数と互換性がなければなりません。 コンバイナ関数は、第2の結果コンテナから第1の結果コンテナに要素を折りたたまなければなりません。- 戻り値:
- リダクションの結果
-
collect
<R,A> R collect(Collector<? super T,A,R> collector)
Collector
を使ってこのストリームの要素に対する可変リダクション操作を実行します。collect(Supplier, BiConsumer, BiConsumer)
の引数として使用される関数をカプセル化したCollector
を使えば、コレクション方針の再利用やcollect操作の合成(マルチレベルのグループ化や分割など)が可能となります。ストリームが並列的であり、
Collector
が並行的
であり、かつストリームが順序付けされていないかコレクタがunordered
である場合、並行リダクションが実行されます(並行リダクションの詳細はCollector
を参照。)これは終端操作です。
並列実行時には、複数の中間結果のインスタンス化、データ設定、およびマージが可能であるため、可変データ構造の隔離を維持できます。 したがって、スレッドセーフでないデータ構造(
ArrayList
など)で並列実行を行う場合でも、並列リダクション用の同期を追加する必要はありません。- APIのノート:
- 次の場合、文字列がArrayList内に蓄積されます。
List<String> asList = stringStream.collect(Collectors.toList());
次の場合、
Person
オブジェクトが市町村別に分類されます。Map<String, List<Person>> peopleByCity = personStream.collect(Collectors.groupingBy(Person::getCity));
次の場合、2つの
Collector
をカスケード接続することにより、Person
オブジェクトが都道府県別、市町村別に分類されます。Map<String, Map<String, List<Person>>> peopleByStateAndCity = personStream.collect(Collectors.groupingBy(Person::getState, Collectors.groupingBy(Person::getCity)));
- 型パラメータ:
R
- 結果の型A
-Collector
の中間蓄積の型- パラメータ:
collector
- リダクションを記述するCollector
- 戻り値:
- リダクションの結果
- 関連項目:
collect(Supplier, BiConsumer, BiConsumer)
,Collectors
-
min
Optional<T> min(Comparator<? super T> comparator)
- パラメータ:
comparator
- このストリームの要素を比較する、非干渉でステートレスなComparator
- 戻り値:
- このストリームの最小要素を記述する
Optional
または空のOptional
(ストリームが空の場合) - 例外:
NullPointerException
- 最小要素がnullの場合
-
max
Optional<T> max(Comparator<? super T> comparator)
- パラメータ:
comparator
- このストリームの要素を比較する、非干渉でステートレスなComparator
- 戻り値:
- このストリームの最大要素を記述する
Optional
または空のOptional
(ストリームが空の場合) - 例外:
NullPointerException
- 最大要素がnullの場合
-
count
long count()
- APIのノート:
- ストリーム・ソースから直接カウントを計算できる場合、実装はストリーム・パイプライン(連続的または並列的に)を実行しないことを選択することがあります。 このような場合、ソース要素はトラバースされず、中間演算は評価されません。 副作用を伴う動作パラメータは、デバッグなどの無害な場合を除いては、強く推奨されません。 たとえば、次のストリームを考えてみましょう:
ストリーム・ソースによってカバーされる要素の数List<String> l = Arrays.asList("A", "B", "C", "D"); long count = l.stream().peek(System.out::println).count();
List
は既知であり、中間操作peek
はストリーム(flatMap
またはfilter
操作の場合のように)に要素を注入または削除しません。 したがって、カウントはList
のサイズであり、パイプラインを実行する必要はなく、副作用としてリスト要素を出力します。 - 戻り値:
- このストリームの要素の個数
-
anyMatch
boolean anyMatch(Predicate<? super T> predicate)
このストリームのいずれかの要素が指定された述語に一致するかどうかを返します。 すべての要素で述語を評価するとは限りません(結果を決定するのに必要でない場合)。 ストリームが空の場合、false
が返され、述語は評価されません。これは短絡終端操作です。
-
allMatch
boolean allMatch(Predicate<? super T> predicate)
このストリームのすべての要素が指定された述語に一致するかどうかを返します。 すべての要素で述語を評価するとは限りません(結果を決定するのに必要でない場合)。 ストリームが空の場合、true
が返され、述語は評価されません。これは短絡終端操作です。
-
noneMatch
boolean noneMatch(Predicate<? super T> predicate)
指定された述語に一致する要素がこのストリーム内に存在しないかどうかを返します。 すべての要素で述語を評価するとは限りません(結果を決定するのに必要でない場合)。 ストリームが空の場合、true
が返され、述語は評価されません。これは短絡終端操作です。
-
findFirst
Optional<T> findFirst()
このストリームの最初の要素を記述するOptional
を返します。ストリームが空の場合は空のOptional
を返します。 ストリームが検出順序を持たない場合は、任意の要素が返されます。これは短絡終端操作です。
- 戻り値:
- このストリームの最初の要素を記述する
Optional
または空のOptional
(ストリームが空の場合) - 例外:
NullPointerException
- 選択された要素がnullの場合
-
findAny
Optional<T> findAny()
ストリームの一部の要素を記述するOptional
を返します。ストリームが空の場合は空のOptional
を返します。これは短絡終端操作です。
この操作の動作は明らかに非決定論的です。ストリームの任意の要素を自由に選択できます。 これは、並列処理でのパフォーマンスを最大化できるようにするためです。デメリットは、同じソースに対して呼び出すたびに、違う結果が返される可能性がある点です。 (安定した結果が必要な場合は、かわりに
findFirst()
を使用してください。)- 戻り値:
- このストリームのある要素を記述する
Optional
または空のOptional
(ストリームが空の場合) - 例外:
NullPointerException
- 選択された要素がnullの場合- 関連項目:
findFirst()
-
builder
static <T> Stream.Builder<T> builder()
Stream
のビルダーを返します。- 型パラメータ:
T
- 要素の型- 戻り値:
- ストリーム・ビルダー
-
empty
static <T> Stream<T> empty()
空の順次Stream
を返します。- 型パラメータ:
T
- ストリーム要素の型- 戻り値:
- 空の順次ストリーム
-
of
static <T> Stream<T> of(T t)
単一要素を含む順次Stream
を返します。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
t
- 単一要素- 戻り値:
- 単一要素の順次ストリーム
-
ofNullable
static <T> Stream<T> ofNullable(T t)
非nullならば、単一の要素を含むシーケンシャルなStream
を返します。それ以外の場合は空のStream
を返します。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
t
- 単一要素- 戻り値:
- 指定された要素が非nullの場合は単一の要素を持つストリーム、そうでない場合は空のストリーム
- 導入されたバージョン:
- 9
-
of
@SafeVarargs static <T> Stream<T> of(T... values)
指定された値を要素に持つ、順序付けされた順次ストリームを返します。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
values
- 新しいストリームの要素- 戻り値:
- 新しいストリーム
-
iterate
static <T> Stream<T> iterate(T seed, UnaryOperator<T> f)
初期要素seed
に関数f
を繰り返し適用することで生成される、順序付けされた無限順次Stream
を返します(seed
、f(seed)
、f(f(seed))
、といった要素から成るStream
が生成される)。Stream
の最初の要素(位置0
)は、指定されたseed
になります。n > 0
の場合、位置n
の要素は、位置n - 1
の要素に関数f
を適用した結果になります。f
を1つの要素に適用するアクションhappens-beforeは、後続の要素にf
を適用するアクションです。 どのような要素に対しても、ライブラリが選択するどのスレッドでもアクションを実行できます。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
seed
- 初期要素f
- 新しい要素を生成するために1つ前の要素に適用される関数- 戻り値:
- 新しい順次
Stream
-
iterate
static <T> Stream<T> iterate(T seed, Predicate<? super T> hasNext, UnaryOperator<T> next)
指定されたnext
関数を初期要素に反復適用することによって生成され、与えられたhasNext
述語を満たすことを条件とする、順次順序付けされたStream
を返します。 ストリームは、hasNext
述部がfalseを返すとすぐに終了します。Stream.iterate
は、対応するforループによって生成されるものと同じシーケンスを生成する必要があります:for (T index=seed; hasNext.test(index); index = next.apply(index)) { ... }
hasNext
述部がシード値を保持しない場合、結果のシーケンスは空になることがあります。 それ以外の場合、最初の要素は指定されたseed
値になります。次の要素(存在する場合)は、next
関数をseed
値に適用した結果、hasNext
述語がストリームを終了する必要があることを示すまで繰り返されます。hasNext
述語を要素happens-beforeに適用するアクション。その要素にnext
関数を適用するアクション。 1つの要素happens-beforeにnext
関数を適用するアクション。後続の要素にhasNext
述語を適用するアクション。 任意の要素に対して、ライブラリが選択したどのスレッドでもアクションを実行できます。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
seed
- 初期要素hasNext
- ストリームを終了する必要があるかどうかを判断する要素に適用する述語。next
- 新しい要素を生成するために前の要素に適用される関数- 戻り値:
- 新しい順次
Stream
- 導入されたバージョン:
- 9
-
generate
static <T> Stream<T> generate(Supplier<? extends T> s)
指定されたSupplier
によって生成される要素を含む、順序付けされていない無限順次ストリームを返します。 これは、定数ストリームやランダムな要素から成るストリームなどを生成するのに適しています。- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
s
- 生成される要素のSupplier
- 戻り値:
- 順序付けされていない新しい無限順次
Stream
-
concat
static <T> Stream<T> concat(Stream<? extends T> a, Stream<? extends T> b)
最初のストリームの全要素と2番目のストリームの全要素を連結したものを要素に持つ、遅延連結ストリームを作成します。 結果のストリームが順序付けされるのは、入力ストリームがどちらも順序付けされている場合であり、並列的になるのは、入力ストリームのどちらかが並列的な場合です。 結果のストリームのクローズ時には、両方の入力ストリームのクローズ・ハンドラが呼び出されます。このメソッドは2つの入力ストリームで動作し、各ストリームをそのソースにバインドします。 その結果、入力ストリーム・ソースへのその後の変更は、連結ストリーム結果に反映されないことがあります。
- APIのノート:
- 最適化の機会を保持するために、このメソッドは各ストリームをそのソースにバインドし、パラメータとして2つのストリームのみを受け入れます。 例えば、各入力ストリーム・ソースの正確なサイズが分かっている場合、連結ストリーム・ソースの正確なサイズを計算することができます。 バインディングなしでストリームを連結する場合、またはこのメソッドへのネストされた呼び出しを行わない場合は、ストリームのストリームを作成し、アイデンティティ関数を使用してフラット・マッピングしてみてください:
Stream<T> concat = Stream.of(s1, s2, s3, s4).flatMap(s -> s);
- 実装上のノート:
- 連結を繰り返すことでストリームを構築する際には注意が必要です。 深く連結されたストリームの要素にアクセスすると、深い呼び出しチェーンや
StackOverflowError
が発生する可能性があります。返されたストリームのシーケンシャル/パラレル実行モードへのその後の変更は、入力ストリームに伝播することが保証されていません。
- 型パラメータ:
T
- ストリーム要素の型- パラメータ:
a
- 最初のストリームb
- 2番目のストリーム- 戻り値:
- 2つの入力ストリームを連結したもの
-
-