Как работают try, except, else и finally?
- Когда выполняется блок else в try?
- Зачем нужен finally?
- Почему нельзя писать голый except?
- Как создать своё исключение?
try — опасный код, except — обработка, else — если ошибки не было, finally — всегда.
- Ловите конкретные исключения, а не
except:и неExceptionбез нужды raise ... from eсохраняет причину исходной ошибки
А ещё Свои исключения наследуют от Exception, обычно с общим базовым классом проекта
Подробно
Порядок выполнения:
- выполняется блок
try; - если возникло исключение, ищется первый подходящий
except(по типу, с учётом наследования) — поэтому более частные исключения пишут выше; - если исключения не было, выполняется
else; - в любом случае в конце выполняется
finally— даже приreturnили необработанной ошибке.
Зачем else: в try оставляют только строку, которая может упасть, а продолжение кладут в else. Так случайно не перехватится ошибка из кода, который вы не собирались защищать.
Зачем finally: освобождение ресурсов — закрыть файл, соединение, снять блокировку. Чаще для этого используют with.
Почему плох голый except:: он ловит всё, включая KeyboardInterrupt и SystemExit, и прячет ошибки. except Exception лучше, но тоже скрывает баги, если за ним нет логирования или повторного raise.
raise NewError(...) from e связывает исключения: в трейсбеке видна исходная причина. Свои исключения делают наследниками Exception — обычно от общего класса проекта (class AppError(Exception)), чтобы их можно было ловить вместе.
Пример
class ConfigError(Exception):
pass
def load(path):
try:
f = open(path, encoding="utf-8")
except FileNotFoundError as e:
raise ConfigError(f"нет файла {path}") from e
else:
with f:
return f.read()
finally:
print("попытка загрузки завершена")Что хотят услышать
- Порядок выполнения всех четырёх блоков.
- Назначение
elseиfinallyна примерах. - Почему нельзя ловить всё подряд.
- Свои исключения и
raise ... from.
Частые ошибки
- Писать
except Exception: pass. - Ставить общий
except Exceptionвыше частных — частные никогда не сработают. - Думать, что
finallyне выполнится приreturnвнутриtry.
Проверьте себя
Один верный вариант. Подумайте, потом откройте ответ.
Показать варианты и ответ
- ✗else выполняется, если было исключение
- ✗finally выполняется, только если исключения не было
- ✓else — если ошибки не было, finally — всегда
- ✗Лучше всегда ловить голый except:
Что спросят дальше
Разбор темы
- Исключения и контекстные менеджеры
try, except, else и finally, свои исключения и цепочки raise from, with и контекстные менеджеры, ExceptionGroup.
Связанные вопросы
Разбор собеседования с sotto
После собеседования sotto разбирает разговор: оценка, каждый вопрос — хорошо, частично или слабо, чего не хватило в ответе и над чем поработать к следующему разу. Первые 30 минут бесплатно.