Разница между Resume и Goto в блоке обработки ошибок

Я понимаю, что в следующем примере вместо оператора Goto следует использовать оператор Resume.

Sub Method()
  On Error Goto ErrorHandler
  ...
CleanUp:
  ...
  Exit Function

ErrorHandler:
  Log error etc

  Err.Clear  'Is this line actually necessary?'

  Resume CleanUp 'SHOULD USE THIS'
  Goto CleanUp  'SHOULD NOT USE THIS'
End Sub

Мой вопрос в том, какая разница в выполнении двух?

Ответы

Ответ 1

Оба передают исполнение на метку Cleanup. Насколько я помню, единственными отличиями являются

  • Использование Goto не очищает объект Err (поэтому Err.Clear необходим, если вы используете Goto), и он не позволяет вашему обработчику ошибок отключиться. Если после метки Cleanup произошла ошибка, она не будет обрабатываться в ErrorHandler.
  • Использование Resume очищает объект Err и снова переключает ваш обработчик ошибок (он отключается, когда он обрабатывает ошибки). Если после Cleanup lable возникает ошибка, она будет обрабатываться в ErroHandler

Вводная запись VB6 для оператора резюме не объясняет эти различия.

Ответ 2

Это БОЛЬШОЕ недоразумение! Существует важная разница между:

Err.Clear
GoTo CleanUp

и

Resume CleanUp

НИКОГДА не используйте первую форму, ВСЕГДА используйте Resume CleanUp (только). Возобновите RESET внутреннего состояния ошибки VB6, поэтому при возникновении ДРУГОЙ ошибки, появится надпись "On Error GoTo Label". Я использую "Err.Clear", тогда объект Err очищается, но внутреннее состояние ошибки НЕ удаляется, и когда возникает другая ошибка, он считается кодом БЕЗ любого обработчика исключений и выдает за пределы функции. Вы НЕ МОЖЕТЕ исправить это, используя "On Error GoTo Label2"

Рассмотрим этот код:

Public Sub Test()
On Error GoTo L1
MsgBox 0 / (1 - 1)
Exit Sub

L1:
  Err.Clear
L0:
  On Error GoTo L2
  MsgBox 0 / (1 - 1) 'ERROR!
  Exit Sub

L2:
  MsgBox Err
End Sub

Если вы запустите это, он будет прерывать "ОШИБКА!". линия. Если вы замените "Err.Clear" на "Resume L0", тогда выполнение не прерывает "ERROR!" строка и код переходят на метку "L2" и предоставляют "MsgBox Err"