try-except-else가 존재하는 이유는 무엇입니까?
try
블록은 당신이 예상되는 오류를 처리 할 수 있습니다. except
블록 만이 처리 할 준비가되어 예외를 포착해야한다. 예기치 않은 오류를 처리하면 코드가 잘못된 일을하고 버그를 숨길 수 있습니다.
else
오류가 없다면 절은 실행됩니다, 그리고에 그 코드를 실행하지 않음으로써 try
블록, 당신은 예기치 않은 오류가 끼지 않도록. 다시 말하지만 예기치 않은 오류를 발견하면 버그가 숨겨 질 수 있습니다.
예
예를 들면 다음과 같습니다.
try:
try_this(whatever)
except SomeException as the_exception:
handle(the_exception)
else:
return something
스위트 룸은 "제외 시도는,"이 개 옵션 조항을 가지고 else
와 finally
. 실제로 try-except-else-finally
입니다.
else
try
블록 에서 예외가없는 경우에만 평가됩니다 . 아래에서보다 복잡한 코드를 단순화 할 수 있습니다.
no_error = None
try:
try_this(whatever)
no_error = True
except SomeException as the_exception:
handle(the_exception)
if no_error:
return something
따라서 else
(버그를 생성 할 수있는) 대안 과를 비교하면 코드 줄이 줄어들고 더 읽기 쉽고 유지 관리가 쉽고 버그가 적은 코드베이스를 가질 수 있습니다.
finally
finally
return 문을 사용하여 다른 행을 평가하는 경우에도 실행됩니다.
의사 코드로 분류
주석과 함께 모든 기능을 보여주는 가능한 가장 작은 형태로 이것을 분류하는 것이 도움이 될 수 있습니다. 의사 코드가 함수 내에 있다고 구문 상으로는 정확하지만 이름을 정의하지 않으면 실행할 수 없다고 가정합니다.
예를 들면 다음과 같습니다.
try:
try_this(whatever)
except SomeException as the_exception:
handle_SomeException(the_exception)
# Handle a instance of SomeException or a subclass of it.
except Exception as the_exception:
generic_handle(the_exception)
# Handle any other exception that inherits from Exception
# - doesn't include GeneratorExit, KeyboardInterrupt, SystemExit
# Avoid bare `except:`
else: # there was no exception whatsoever
return something()
# if no exception, the "something()" gets evaluated,
# but the return will not be executed due to the return in the
# finally block below.
finally:
# this block will execute no matter what, even if no exception,
# after "something" is eval'd but before that value is returned
# but even if there is an exception.
# a return here will hijack the return functionality. e.g.:
return True # hijacks the return in the else clause above
우리가 사실입니다 수 의 코드 포함 else
에 블록 try
은 예외가 없다면 실행할 수 있지만 것입니다 경우, 대신 블록 무슨 코드 자체는 우리가 잡고있는 종류의 예외가 발생하는 경우? try
블록에 그대로두면 버그가 숨겨집니다.
우리는 코드에서 try
실패하면 큰 실패를 원한다는 원칙 하에서 예상치 못한 예외를 피하기 위해 블록 의 코드 줄을 최소화 하려고합니다. 이것이 가장 좋은 방법 입니다.
예외는 오류가 아니라는 것을 이해합니다.
파이썬에서 대부분의 예외는 오류입니다.
pydoc을 사용하여 예외 계층을 볼 수 있습니다. 예를 들어, 파이썬 2에서 :
$ python -m pydoc exceptions
또는 파이썬 3 :
$ python -m pydoc builtins
우리에게 계층 구조를 제공합니다. Exception
파이썬은 엔딩 for
루프 ( StopIteration
) 와 같은 것들에 대해 일부를 사용하지만 대부분의 종류의 오류가 있음을 알 수 있습니다 . 이것은 파이썬 3의 계층입니다 :
BaseException
Exception
ArithmeticError
FloatingPointError
OverflowError
ZeroDivisionError
AssertionError
AttributeError
BufferError
EOFError
ImportError
ModuleNotFoundError
LookupError
IndexError
KeyError
MemoryError
NameError
UnboundLocalError
OSError
BlockingIOError
ChildProcessError
ConnectionError
BrokenPipeError
ConnectionAbortedError
ConnectionRefusedError
ConnectionResetError
FileExistsError
FileNotFoundError
InterruptedError
IsADirectoryError
NotADirectoryError
PermissionError
ProcessLookupError
TimeoutError
ReferenceError
RuntimeError
NotImplementedError
RecursionError
StopAsyncIteration
StopIteration
SyntaxError
IndentationError
TabError
SystemError
TypeError
ValueError
UnicodeError
UnicodeDecodeError
UnicodeEncodeError
UnicodeTranslateError
Warning
BytesWarning
DeprecationWarning
FutureWarning
ImportWarning
PendingDeprecationWarning
ResourceWarning
RuntimeWarning
SyntaxWarning
UnicodeWarning
UserWarning
GeneratorExit
KeyboardInterrupt
SystemExit
논평자가 물었다 :
외부 API를 핑하는 메소드가 있고 API 랩퍼 외부의 클래스에서 예외를 처리하려고한다고 가정하십시오. e가 예외 오브젝트 인 경우 except 절의 메소드에서 e를 간단히 리턴합니까?
아니요, 예외를 반환하지 않고 raise
스택 추적을 유지하기 위해 예외를 다시 발생 시킵니다.
try:
try_this(whatever)
except SomeException as the_exception:
handle(the_exception)
raise
또는 Python 3에서는 예외 체인을 사용하여 새 예외를 발생시키고 역 추적을 유지할 수 있습니다.
try:
try_this(whatever)
except SomeException as the_exception:
handle(the_exception)
raise DifferentException from the_exception
나는 여기 에 내 대답을 자세히 설명 합니다 .