2012-01-05 1 views
0

this answer 메시지가 표시되는 scala-arm 라이브러리를보고 있으며 대부분의 컨텍스트에서 리소스를 관리하는 데 적합합니다.Scala에서 닫을 수있는 리소스를 전달하는 가장 좋은 방법은 무엇입니까?

처음에는 리소스를 다른 리소스로 "전달"하지 않는 한 가지 상황이 있습니다. I/O 작업을 할 때이 자주 온다 : 이제

for (fin <- managed(new FileInputStream(file)); 
    // almost what we want, except see below 
    gzip <- managed(new GZIPInputStream(fin)); 
    src <- managed(Source.fromInputStream(gzip))) { 
    /* some fancy code */ 
} 

, 문제는이입니다 gzip이 성공적으로 생성되는 경우, 지느러미을 닫는에 대한 책임이며, 지느러미이 안 폐쇄 됨 (업데이트 : 이것은 적절하지 않습니다 - 이중 닫기가 좋습니다; 승인 된 답변 참조). 하지만 대안 :

for (src <- managed(Source.fromInputStream(
       new GZIPInputStream(new FileInputStream(file))))) { 
    /* some fancy code */ 
} 

꽤 정확하지 않는 경우 - GZIPInputStream 생성자의 (틀림없이 가능성)에 에러가 발생했을 경우는 FileInputStream이 닫히지 않았습니다. 위도 : fromInputStream.

scala-arm (또는 다른 패키지)은 내가 아직 발견하지 못한이 정리를 안전하게 처리 할 수있는 기능을 제공합니까?

답변

3

몇 분 더보고 있었는데 정말 중요하지 않은 것으로 나타났습니다. java.io.Closeable은 이미 닫힌 리소스를 no-op로 지정합니다. 따라서 모든 것을 managed으로 감싸서 두 번 닫는 것이 안전합니다. 따라서 첫 번째 코드 예는 정확합니다.

1

필자에게 가장 좋은 방법은 기능 세계에서 자금을 지원하는 iteratee, enumerator 및 enumeratee의 개념을 사용하는 것입니다.

관심있는 대상은 Scalaz 라이브러리입니다.이 라이브러리는 아주 잘 구현되어 있습니다.

어떤 개념에서는 개념을 사용하여 소스의 반복자가 언제 consumming이 끝났는지를 알게되고 다른 방법으로 돌아 가게합니다. 죄수가 소스를 알고 있다는 것은 제공 할 것이 없습니다.

편집 여기

는 iteratee가 무엇인지에 대한 아주 명확 post입니다. 문제에 대해 이야기하는 동기 매개 변수를 참조하십시오. 무엇이 잘못 되었든 잘못되었지만 적절한시기에 자원을 닫습니다.

+0

저는 "무엇보다 소스가 아무것도 없다는 사실을 알고 있습니다. 제공한다 ". 내가 끝내면 내 문제는 끝나지 않았다. succcessfully 입력 체인을 설정할 수없는 경우에도 파일이 닫혔는지 확인하는 것이 었습니다. –

+0

실제로이 iteratee, enumerator 및 enumeratee는 두 가지 (및 기타) 경우를 해결하기 위해 있습니다. Source가 생산을 마쳤을 때 (당신이 상관하지 않는 것) Consumer가 끝났을 때 (그리고 실제로 실패하면 끝났습니다). 나는 그 주제에 당신을 밝힐 매우 유용한 게시물을 추가 할 것입니다. ** ** 당신의 관심사에 대한 해결책입니다 ** –

+0

고마워요. 그 게시물은 많은 도움이됩니다. 흥미로운 솔루션 인 것처럼 보이지만 모든 것이 Iteratees를 기반으로한다고 가정합니다. 자바의 표준 필터링 된 스트림과 리더를 직접 사용하는 것처럼 보이지는 않지만, 그들은 Iteratees에 대해 아무 것도 모른다. –