Файл без with
Почему open без with однажды кончается сообщением «слишком много открытых файлов».
Как надо
with open(imya, encoding="utf-8") as fayl:
dannye = fayl.read()
Файл закрывается сам — и при обычном выходе, и когда внутри случилась ошибка.
Что не так без with
fayl = open(imya, encoding="utf-8")
dannye = fayl.read()
fayl.close()
Если между открытием и close случится исключение, файл останется
открытым. Программа продолжит работу, ничего не заметив.
У процесса есть предел числа открытых файлов — обычно около тысячи. Программа, которая читает файлы в цикле и изредка спотыкается, исчерпает его через несколько часов и упадёт с сообщением про «слишком много открытых файлов» — в месте, никак не связанном с настоящей причиной.
Запись опаснее чтения
Несохранённые данные остаются в буфере и попадают на диск при закрытии. Файл, не закрытый явно, может оказаться пустым или обрезанным — а программа при этом отработала «успешно».
Несколько файлов сразу
with open(vhod, encoding="utf-8") as v, \
open(vyhod, "w", encoding="utf-8") as z:
...
Оба закроются вместе. Это лучше вложенных with: уровень отступа не
растёт.
with не только для файлов
Тот же приём работает с блокировками, соединениями к базе, временными
папками — со всем, что надо вернуть на место. Если в чужой библиотеке
есть объект, который «надо закрыть», почти наверняка он умеет with.