Проблемы с проверкой существования файла Python - если я не добавляю оператор печати
Я переношу программу из Python2 (не знаю точной версии) на Python3.3 и обновляю несколько вещей, но этот цикл, который проверяет существование набора недавно доступных путей к файлам против реальных файлов аварии.
for index in range(story.recentFiles.GetCount()):
try:
if not os.path.exists(story.recentFiles.GetHistoryFile(index)): pass
except IOError:
self.RemoveRecentFile(story, index)
break
Доступ к одному файлу отлично работает, поэтому это связано с циклом. Если я пройду через цикл с помощью отладчика, код будет работать нормально, но если я просто запустил приложение, он выйдет из строя, когда ошибка "python.exe перестала отвечать".
Самая странная часть, однако, должна состоять в том, что когда я добавляю оператор печати перед os.path.exists
, он работает с обычным прохождением:
for index in range(story.recentFiles.GetCount()):
try:
print('test') # Why does printing this make it not crash??
if not os.path.exists(story.recentFiles.GetHistoryFile(index)): pass
except IOError:
self.RemoveRecentFile(story, index)
break
Что с этим связано? Я предполагаю, что он имеет какое-то отношение к скорости цикла и времени доступа к файлу или что-то, потому что медленный шаг позволяет ему выполнять штраф, но я честно не знаю, в чем проблема.
Ответы
Ответ 1
С подробностями трудно сказать, но вот теория: когда вы добавляете print
, это фактически вызывает IOError (это возможно, поскольку документировано), который пойман, а os.path.exists(story.recentFiles.GetHistoryFile(index))
не выполняется, поэтому ваша программа не зависает.
Вы можете протестировать это с помощью теста, подобного следующему (до кода, который вы указываете):
try:
print('test')
except IOError:
with open('ioerror_raised.txt', 'w'):
pass
который создаст файл ioerror_raised.txt
, если print
поднял IOError
.
Это может объяснить, почему добавление print
делает запуск кода.
(Если это так, то os.path.exists(story.recentFiles.GetHistoryFile(index))
следует явно отлаживать.)
Ответ 2
В начале цикла создается статический список допустимых индексов (с диапазоном()), но вы удаляете файлы из списка (RemoveRecentFile) внутри цикла.
Таким образом, ваша проблема может заключаться в том, что вы запускаете цикл с 10 файлами, удаляете один файл (например, индекс 4), потому что вы не можете получить к нему доступ, а затем попытайтесь получить доступ к файлу 10-го файла (индекс 9), который не является там, потому что вы переместили 5 > 4, 6- > 5, 7- > 6, 8- > 7, 9- > 8
Ответ 3
Вы взаимодействуете с некорректно написанным кодом C/С#/С++, поэтому трудно указать, где ошибка.
То, что оно плохо написано, очевидно из того, как API заставляет вас получать элементы списка с помощью вызова, а не просто использовать индекс.
Удачи!
Ответ 4
Я не уверен, что вы портируете свой код вручную, но вы всегда можете попробовать автоматизированный инструмент:
http://docs.python.org/2/library/2to3.html