2016-12-19 4 views
0

큰 파일 세트 (각 2-3GB 정도)가 있는데 InputStream을 사용하여이 파일을 읽고 새 파일로 출력해야합니다.InputStream 파일 및 출력 부분을 읽습니다.

//this is just for example 
int size=100; 
String src="pathtofile"; 
OutputStream os = null; 
Inputstream is = new FileInputStream(new File(src)); 
byte[] buffer = new byte[size]; 
byte[] bufferis = getBytesFromIS(is); 

buffer=Arrays.copyOfRange(bufferis,0,buffer.length); 

String tempstr=new String(buffer); 
byte[] tempBytes=Arrays.copyOfRange(bufferis, buffer.length,is.available()); 
os = new FileOutputStream(new File(dest)); 
copy(new ByteArrayInputStream(tempBytes), os); //function writing to file 

이 작은 파일이 잘 작동하지만, 큰 파일에 사용할 때, 나는 여전히 OutOfMemoryError을 받고, -Xmx6114m을 설정하는 경우에도, OutOfMemoryError 점점 계속.

+0

대신 2GB 데이터를 처리 할 수있는 프린트 라이저를 사용해보십시오 .... – SmashCode

+0

여기에 대한 대답은 놀랍도록 간단 할 수 있습니다 : 전체 파일을 작은 부분 만 필요할 때 읽지 마십시오! 'InputStream'을 사용할 이유가 있습니까? 스트림은 종종 더 다재다능하지만,이 특정 사용 사례는'RandomAccessFile'을 사용하면 훨씬 쉽게 해결할 수 있습니다. – Marco13

+0

'bufferis'를 제거해야합니다. 당신이 할 수있는'int bytesRead = is.read (buffer);' – roby

답변

0

최대 배열 길이는 Integer.MAX_VALUE보다 약간 작습니다. 즉, 2e9입니다. 따라서 전체를 byte[]으로 읽을 수없고 다른 것을 사용해야합니다. ByteByffer이 아마도 가장 빠른 솔루션 일 것입니다 (메모리 매핑 된 파일).

+0

이 경우 bytebuffer에 inputstream을 어떻게 읽습니까? – user2324644

+0

@ user2324644 https://docs.oracle.com/javase/8/docs/api/java/nio/channels/FileChannel.html#map-java.nio.channels.FileChannel.MapMode-long-long- – maaartinus

+0

bytebuffer를 사용하면 여전히 3GB 이상의 파일 크기를 처리 할 수 ​​없습니다. – user2324644

1

getBytesFromIS(is)을 표시하지 않지만 전체 파일을 읽는다고 가정하면 필요하지 않습니다.

가장 쉬운 방법은 이미이 기능을 제공하며 완전히 테스트 된 라이브러리를 사용하는 것입니다. 예 : Apache Commons IOUtils.

그렇지 않으면 오프셋 길이 0에서 원하는 길이로 시작하여 InputStream.read(b, off, len)을 사용할 수 있습니다. 그러나이 함수는 이 아니므로은 원하는 모든 데이터를 읽을 수 있음을 유의하십시오.

+0

입력 스트림을 만들 필요가있다, 파일 inputstream 여전히 바이트 버퍼에로드됩니다, 그래서 내가 잘못 착각하지 않으면 메모리 오류가 될 것이라고 가정합니다. – user2324644

+0

IOUtils .toByteArray (inputstream) 이것은 크기 문제로 인해 여전히 작동하지 않을 것입니다. – user2324644

+0

@ user2324644 -'IOUtils.toByteArray (inputstream)'는 링크의 함수가 아닙니다. – kdgregory