try — 오류와 예외를 잡아 처리하기
try — 오류와 예외를 잡아 처리하기
Tcl에서 오류를 안전하게 처리하려면 try 명령어가 중심이 돼요. 다른 언어의 try/catch/finally와 비슷하면서도, Tcl 특유의 예외 코드(ok, error, return, break, continue) 개념이 더해져 있어요. body 스크립트를 실행하고, 그 결과(정상 종료든 오류든)에 따라 맞는 핸들러를 골라 실행해주고, finally 절이 있으면 그건 어떤 경우에도 반드시 실행해주는 식이죠.
출처: 문서
본문
문법
try body ?handler...? ?finally script?
try는 스크립트 body를 실행하고, 그 스크립트의 결과(정상 종료, 오류, 그 밖의 예외적 결과)에 따라 해당하는 핸들러 스크립트를 실행해 그 상황을 처리해요. 이 모든 과정이 끝난 뒤 finally 절이 있으면 그 안의 스크립트를 실행하고, 핸들러(또는 매칭된 핸들러가 없으면 body)의 결과는 그대로 전파되도록 둬요. 주의할 점은 finally 절은 오류가 발생해도, 어떤 핸들러가 쓰였는지와 무관하게 항상 처리된다는 거예요.
핸들러 절은 각각 여러 단어로 표현되며, 반드시 다음 형태 중 하나여야 해요.
on code variableList script
이 절은 body의 평가가 예외 코드 code로 끝났을 때 매칭돼요. code는 정수로도 쓸 수 있고, 리터럴 단어 ok, error, return, break, continue로도 쓸 수 있어요. 이 리터럴들은 각각 정수 0부터 4까지에 대응해요.
trap pattern variableList script
이 절은 body의 평가가 오류로 끝났고, 인터프리터의 상태 딕셔너리에 있는 -errorcode의 앞부분이 pattern과 같을 때 매칭돼요. -errorcode에서 가져오는 앞부분 단어의 수는 pattern의 리스트 길이와 같고, 비교할 때는 -errorcode와 pattern 모두 단어 사이 공백이 정규화돼요.
각 핸들러의 variableList 단어는 항상 변수 이름들의 리스트로 해석돼요. 리스트의 첫 단어가 존재하고 비어 있지 않으면, 그 이름을 가진 변수에 body 평가의 결과(사람이 읽을 수 있는 형태의 오류 포함)가 들어가요. 두 번째 단어가 존재하고 비어 있지 않으면, 그 이름을 가진 변수에 body 실행이 끝나는 순간의 인터프리터 옵션 딕셔너리가 들어가요.
각 핸들러의 script 단어도 항상 같은 방식으로 해석돼요. 절이 매칭되면 평가할 Tcl 스크립트이죠. script가 리터럴 -이고 그 핸들러가 마지막 핸들러가 아니면, 대신 다음 핸들러의 스크립트가 호출돼요(switch 명령어와 같은 방식).
핸들러 절은 순서대로 매칭되며, 첫 번째로 매칭되는 것이 항상 선택돼요. 핸들러 절은 많아야 하나만 선택되고, 그 결과 on error는 try 안에서 이후의 모든 trap을 가려버려요. 또한 on error는 trap {}과 동등해요.
핸들러나 finally 절 평가 중에 예외(즉 ok가 아닌 결과)가 발생하면, 원래 예외의 상태 딕셔너리가 새 예외의 상태 딕셔너리에 -during 키 아래 추가돼요.
예제
어떤 일이 있어도 파일이 닫히는 것을 보장하려면:
set f [open /some/file/name a]
try {
puts $f "some message"
# ...
} finally {
close $f
}
파일을 읽기용으로 열 수 없는 여러 이유를 각각 다르게 처리하려면:
try {
set f [open /some/file/name r]
} trap {POSIX EISDIR} {} {
puts "failed to open /some/file/name: it's a directory"
} trap {POSIX ENOENT} {} {
puts "failed to open /some/file/name: it doesn't exist"
}
더 알아보기
catch,error,return,throw— Tcl의 다른 오류·예외 처리 명령어- 관련 키워드:
cleanup,error,exception,final,resource management