Java InputStream na Byte Array a ByteBuffer

1. Prehľad

V tomto rýchlom výučbe sa pozrieme na to, ako previesť súbor InputStream do a byte [] a ByteBuffer - najskôr pomocou obyčajnej Javy, potom pomocou Guava a Commons IO.

Tento článok je súčasťou série „Java - Späť na základné“ tu na Baeldungu.

2. Konvertujte na Byte Array

Pozrime sa na získanie bajtového poľa z jednoduchých vstupných tokov. Dôležitým aspektom bajtového poľa je to umožňuje indexovaný (rýchly) prístup ku každej 8-bitovej (bajtovej) hodnote uloženej v pamäti. Preto môžete s týmito bajtmi manipulovať, aby ste ovládali každý bit. Ideme sa pozrieť na to, ako previesť jednoduchý vstupný tok na a byte [] - najskôr pomocou obyčajnej Javy, potom pomocou Guava a Apache Commons IO.

2.1. Prevod pomocou obyčajnej Javy

Začnime riešením Java zameraným na prácu s prúdom pevnej veľkosti:

@Test public void givenUsingPlainJava_whenConvertingAnInputStreamToAByteArray_thenCorrect () vyvolá IOException {InputStream initialStream = nový ByteArrayInputStream (nový bajt [] {0, 1, 2}); byte [] targetArray = nový bajt [initialStream.available ()]; initialStream.read (targetArray); }

V prípade streamu v medzipamäti - keď pracujeme s prúdom v medzipamäti a nevieme presnú veľkosť podkladových údajov, musíme implementáciu flexibilnejšie:

@Test public void givenUsingPlainJavaOnUnknownSizeStream_whenConvertingAnInputStreamToAByteArray_thenCorrect () vyvolá IOException {InputStream je = nový ByteArrayInputStream (nový bajt [] {0, 1, 2}); // nie naozaj neznáme ByteArrayOutputStream buffer = nový ByteArrayOutputStream (); int nRead; byte [] dáta = nový bajt [1024]; while ((nRead = is.read (data, 0, data.length))! = -1) {buffer.write (data, 0, nRead); } buffer.flush (); byte [] byteArray = buffer.toByteArray (); }

Počnúc jazykom Java 9 to môžeme dosiahnuť dedikovanou metódou InputStream:

@Test public void givenUsingPlainJava9_whenConvertingAnInputStreamToAByteArray_thenCorrect () vyvolá IOException {InputStream je = nový ByteArrayInputStream (nový bajt [] {0, 1, 2}); byte [] data = is.readAllBytes (); }

2.2. Prevod pomocou Guavy

Pozrime sa teraz na jednoduché riešenie založené na Guave - pomocou pohodlnej triedy nástrojov ByteStreams:

@Test public void givenUsingGuava_whenConvertingAnInputStreamToAByteArray_thenCorrect () vyvolá IOException {InputStream initialStream = ByteSource.wrap (nový bajt [] {0, 1, 2}). OpenStream (); byte [] targetArray = ByteStreams.toByteArray (initialStream); }

2.3. Prevod pomocou Commons IO

A na záver - priame riešenie pomocou Apache Commons IO:

@Test public void givenUsingCommonsIO_whenConvertingAnInputStreamToAByteArray_thenCorrect () vyvolá IOException {ByteArrayInputStream initialStream = nový ByteArrayInputStream (nový bajt [] {0, 1, 2}); byte [] targetArray = IOUtils.toByteArray (initialStream); }

Metóda IOUtils.toByteArray () vyrovnáva vstup interne, takže existuje nie je potrebné používať a BufferedInputStream inštancia keď je potrebné ukladanie do vyrovnávacej pamäte.

3. Previesť na ByteBuffer

Teraz sa pozrime na získanie a ByteBuffer z an InputStream. Toto je užitočné kedykoľvek potrebujeme vykonať rýchle a priame nízkoúrovňové I / O operácie v pamäti.

Pri použití rovnakého prístupu ako v predchádzajúcich častiach sa pozrieme na to, ako previesť InputStream do a ByteBuffer - najskôr pomocou obyčajnej Javy, potom pomocou Guava a Commons IO.

3.1. Prevod pomocou obyčajnej Javy

V prípade bajtového toku - poznáme presnú veľkosť podkladových údajov. Použime ByteArrayInputStream # k dispozícii metóda na načítanie bajtového toku do a ByteBuffer:

@Test public void givenUsingCoreClasses_whenByteArrayInputStreamToAByteBuffer_thenLengthMustMatch () vyvolá IOException {byte [] vstup = nový bajt [] {0, 1, 2}; InputStream initialStream = nový ByteArrayInputStream (vstup); ByteBuffer byteBuffer = ByteBuffer.allocate (3); while (initialStream.available ()> 0) {byteBuffer.put ((byte) initialStream.read ()); } assertEquals (byteBuffer.position (), input.length); }

3.2. Prevod pomocou Guavy

Pozrime sa teraz na jednoduché riešenie založené na Guave - pomocou pohodlného ByteStreams úžitková trieda:

@Test public void givenUsingGuava__whenByteArrayInputStreamToAByteBuffer_thenLengthMustMatch () vyvolá IOException {InputStream initialStream = ByteSource .wrap (nový bajt [] {0, 1, 2})) .openStream (); byte [] targetArray = ByteStreams.toByteArray (initialStream); ByteBuffer bufferByte = ByteBuffer.wrap (targetArray); while (bufferByte.hasRemaining ()) {bufferByte.get (); } assertEquals (bufferByte.position (), targetArray.length); }

Tu použijeme while metódu zostáva ukázať iný spôsob načítania všetkých bajtov do súboru ByteBuffer. V opačnom prípade by tvrdenie zlyhalo, pretože ByteBuffer pozícia indexu bude nulová.

3.3. Prevod pomocou Commons IO

A nakoniec - pomocou Apache Commons IO a IOUtils trieda:

@Test public void givenUsingCommonsIo_whenByteArrayInputStreamToAByteBuffer_thenLengthMustMatch () vyvolá IOException {byte [] vstup = nový bajt [] {0, 1, 2}; InputStream initialStream = nový ByteArrayInputStream (vstup); ByteBuffer byteBuffer = ByteBuffer.allocate (3); ReadableByteChannel channel = newChannel (initialStream); IOUtils.readFully (kanál, byteBuffer); assertEquals (byteBuffer.position (), input.length); }

4. Záver

Tento článok ilustroval rôzne spôsoby prevodu surového vstupného toku na bajtové pole a ByteBuffer pomocou obyčajného Java, Guava a Apache Commons IO.

Implementáciu všetkých týchto príkladov nájdete v našom projekte GitHub.