2015-01-07 15 views
11

Java 8には、java.util.stream.Streamおよびjava.util.stream.IntStreamタイプがあります。 java.util.Arraysメソッドバイト配列をIntStreamに変換する最良の方法は何ですか?

IntStream is = Arrays.stream(int[]) 

しかし短い[]またはchar []、intに各要素を拡大、[]バイトからIntStreamを作るそのような方法を有しています。 byte []からIntStreamを作成するための慣用的な方法がありますか?機能的にバイト配列を操作できますか?

私はもちろん自明のバイトが[] IntStream.Builder手動で[] int型と使用Arrays.stream(INT [])、または使用するように変換することができます:

public static IntStream stream(byte[] bytes) { 
    IntStream.Builder isb = IntStream.builder(); 
    for (byte b: bytes) 
     isb.add((int) b); 
    return isb.build(); 
} 

をどちらもが原因非常に機能的ですソースのコピー。

また、InputStream(またはこの場合はByteArrayInputStream)をIntStreamに変換する簡単な方法はないようですが、これはInputStreamを機能的に処理するのに非常に便利です。 (目立たない欠点?)

効率的でコピーしないより機能的な方法がありますか? InputStreamについては

+0

関連するすべての 'byte'は' int'考慮すべき?あるいは、4バイトごとに 'int'と考えるべきでしょうか? –

+0

すべてのバイトがintに拡張されます。たとえば、ファイルまたは他のバイトストリーム内のすべてのバイトのヒストリカルグラムを計算したいとします。 – djb

+0

ストリームAPIを使用してInputStreamからバイトを読み取る理由を教えてください。 InputStreamの読み込みはシーケンシャルなので、以前のメソッドを使用して読み込む方がはるかに高速です。何らかの方法で個々のバイトの順序付きストリームを並列処理できないためです。 InputStreamの並列処理*チャンク*から多くの利点を得るかもしれません... –

答えて

17
byte[] bytes = {2, 6, -2, 1, 7}; 
IntStream is = IntStream.range(0, bytes.length).map(i -> bytes[i]); 

ByteArrayInputStream inputStream = new ByteArrayInputStream(bytes); 
IntStream is2 = IntStream.generate(inputStream::read).limit(inputStream.available()); 
+3

'generate'に' limit'を追加してください。さもなければ、無限の 'Stream'を返します。 –

+0

@SotiriosDelimanolisありがとう。編集しました。 –

+0

私はこれをbyte []〜IntStream部分の答えとして投票しています。ただし、InputStream.available()はByteArrayInputStreamには有効ですが、すべてのInputStreamに対して正確ではないため、ストリームを制限するためにストリームを使用すると、一般的に使用される場合はストリームが切り捨てられることがあります。一般的なInputStreamとIntStreamの問題に別の解決策がありますか? – djb

9
public static IntStream stream(byte[] bytes) { 
    ByteBuffer buffer = ByteBuffer.wrap(bytes); 
    return IntStream.generate(buffer::get).limit(buffer.remaining()); 
} 

(これは簡単にByteBuffer、すなわちからint Sを取るように変更することができます。4バイトintに。)

、あなたが熱心にそれを消費したい場合は、単に読みそれをbyte[]に入れて上記を使用してください。遅延を消費したい場合は、InputStreamInputStream::readとしてConsumer(例外処理に加えて)として生成し、ストリームの終わりに達したら終了してください。

に関してはどちらもが、それはそれは非機能的になり、なぜ私が表示されていないため、ソース

のコピーに非常に機能的です。また

+1

ボーナスポイントについては、buffer.get()のメソッドリファレンスを使用してください: 'IntStream.generate(buffer :: get).limit(buffer.remaining ()) ' – prunge

+1

@prunge私はそれに反対していません。 –

関連する問題