2017-12-06 3 views
-8

파일 I/O (pdf, jpg 등) 전용 응용 프로그램 빌드. 최대 파일 크기는 300MB가 될 수 있습니다. 응용 프로그램은 Linux 64 비트에 배포됩니다. 전통적인 IO 차단 (FileOutputStream 등)을 시도했습니다. 그러나 좋은 성능을 가진 비 차단 또는 더 나은 접근 방법을 찾고 있습니다.파일 크기가 300MB (최대) 인 고성능 파일 I/O Java API

여기에 제가 지금 사용하고있는 코드가 있습니다.

FileOutputStream imageOutFile = new FileOutputStream("path/filename"); 
imageOutFile.write(byteArray); 
imageOutFile.close(); 

이 시나리오를 충족시키기위한 더 나은 접근 방법과 코드 스 니펫을 도와주세요. 휴식 서비스는 파일 메타와 바이트 스트림을 입력하여 내 서비스에 입력하게됩니다.

+4

적어도 혼자서 주제에 대해 연구하고 * 어떤 종류의 결과를 기대할 수 있습니까? 필드에 따라 "고성능"기준은 2ms 또는 400ms 일 수 있습니다. 불행히도 그 주에서 아무도 당신에게 정확하게 대답하지 않을 것입니다. –

+0

파일에 포함 된 데이터의 대상은 무엇입니까? 램? ZIP 파일? Jar 파일? GZIP 파일? 다른 보관 파일입니까? 다른/새로운 파일? 소켓? 다른 출력 목적지가 있습니까? – Wayne

+2

첫째, 파일 R/W 성능은 저장 장치에 따라 크게 달라집니다. 300 MB는 그다지 크지 않지만 크기는 큽니다! – Zico

답변

0

메모리 매핑 된 파일을 사용하는 것이 좋습니다. 우리는 최대 40 배의 메인 메모리 크기로 설정된 데이터에 대해 빠르고 공유 된 읽기/쓰기 액세스를 위해 이들을 사용했습니다.

MappedByteBuffer를 RandomAccessFile에서 사용할 수도 있고, 광산과 같은 라이브러리를 사용할 수도 있습니다.

는 낮은 수준의 파일 메모리 액세스

https://github.com/OpenHFT/Chronicle-Bytes/blob/master/src/test/java/net/openhft/chronicle/bytes/MappedMemoryTest.java

메모리에 내장 된 전용 큐/저널 파일을 매핑 추가합니다. https://github.com/OpenHFT/Chronicle-Queue

메모리 매핑 된 파일에 키/값 저장소가 내장되어 있습니다. https://github.com/OpenHFT/Chronicle-Map

은 참고로 제가 사용한 위의 코드는 25MB의 pdf 파일을 작성하는 약 75ms했다.

나는 당신이 Mb (Megabits)가 아닌 25 MB (메가 바이트)를 의미한다고 가정하고, 단일 데스크탑 SSD에 대해 합리적인 333 MB/s로 변환합니다. 즉, 문제는 디스크 하위 시스템이 수행 할 수있는 작업의 한계에서 작업하고 있다는 것입니다.

BTW $ 1000 미만의 가격으로 약 2GB/s까지 처리 할 수있는 NVMe 드라이브를 구입할 수 있습니다.

+1

호기심 많은 (그리고 여유 시간이 많은) 메모리 맵핑 된 파일은 반복적으로 액세스되는 아주 큰 파일이 거의 없다면 훌륭합니다. 그것의 파일 서버가 진짜로 어떤 여분 이점을주는 경우에? 그것은 또한 정리를 까다롭게 만든다. 왜 최상위 K 액세스를 위해 버퍼를 캐시하지 않는 것이 좋을까요? – amritanshu

+2

@amritanshu OP가 많은 파일을 만들고 닫는 경우, 매핑 된 메모리가 도움이되지 않아 일이 더 복잡해 질 수 있습니다. 액세스 패턴은 기본 디스크 하위 시스템 인 경우보다 빠른 디스크가 필요한 경우 한계에 가깝게 작업하는 것이 더 가능성이 높습니다. –

+1

예! 승리를위한 더 빠른 디스크! : D – amritanshu

-1

기존 코드에해야 할 일은 따라서, BufferedOutputStream을 사용하는 것입니다

OutputStream imageOutFile = new BufferedOutputStream(new FileOutputStream("path/filename")); 

이것은 상당한 차이를 만들 것입니다.

Java에서 파일 I/O가 존재하더라도 비 차단 API가 더 빠르다고 믿을 수있는 정확한 이유는 없습니다.

미리 출력 크기를 알고있는 경우 MappedByteBuffer을 사용할 수는 있지만 그렇게 할 수는 없습니다.

+0

@downvoter 귀하의 설명 부탁드립니다. 이런 종류의 일은 여기에 게시하는 것에 대한 나의 열의를 제기하지 않습니다. – EJP

+0

나는 downvote하지 않았다, 나는 그것을 감당할 평범한 평판이 있지만, 성능과 빠른 차이가 있습니다. 비동기 코드는 코드를 차단하는 것보다 성능이 좋으며 AsynchronousFileChannel은 OS의 기본 인터페이스를 사용하므로 존재하는 asynch 파일 IO 라이브러리가 있습니다. – amritanshu

+0

@amritanshu 성능과 속도의 차이점을 설명하고 논 블로킹 및 비동기 입출력이 동일한 두 가지 이름이 아니라 두 가지 이름임을 설명합니다. 그렇지 않으면'SocketChannel'과'AsynchronousSocketChannel'을 모두 가질 수 없습니다. 자바에는 비 차단 'FileChannel' 변형이 없습니다. – EJP