2010-06-08 40 views
13

Tôi hiểu rằng trong ví dụ sau, một câu lệnh Resume nên được sử dụng thay cho câu lệnh Goto.Sự khác biệt giữa Tiếp tục và Goto trong khối xử lý lỗi

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 

Câu hỏi của tôi là có sự khác biệt nào trong việc thực hiện cả hai?

Trả lời

21

Cả hai thực thi chuyển giao cho nhãn Cleanup. Theo như tôi có thể nhớ, sự khác biệt duy nhất là

  • Sử dụng Goto không rõ ràng đối tượng Err (vì vậy Err.Clear là cần thiết nếu bạn sử dụng Goto) và nó để lại xử lý lỗi của bạn bị vô hiệu hóa. Nếu xảy ra lỗi sau nhãn Cleanup, nó sẽ không được xử lý tại ErrorHandler.
  • Sử dụng Resume xóa đối tượng Err và nó sẽ bật lại trình xử lý lỗi của bạn (nó bị vô hiệu hóa trong khi xử lý lỗi). Nếu lỗi xảy ra sau khi số Cleanup lable, lỗi sẽ được xử lý tại ErroHandler

VB6 manual entry for the Resume statement không giải thích những khác biệt này.

+0

Chúc mừng MarkJ, không thể tìm được câu trả lời này. –

+1

Trong khi thử nghiệm tôi đã thấy rằng nếu một lỗi được nêu ra trong CleanUp một vòng lặp infinte sẽ tồn tại nảy giữa các khối ErrorHandler và CleanUp. Do đó, kỹ thuật được khuyến nghị có On Error Resume Next trong CleanUp không? –

+0

@Rich Oliver Vâng, đó là những gì tôi làm. Xem câu hỏi này http://stackoverflow.com/questions/536379/how-do-you-handle-errors-in-error-handlers-in-vb6 hoặc thậm chí xem qua các câu hỏi khác được gắn thẻ 'vb6' và' error-handling' http://stackoverflow.com/questions/tagged?tagnames=vb6%2berror-handling&sort=votes&pagesize=15 – MarkJ

2

Đây là sự hiểu lầm lớn! Có khác biệt quan trọng giữa:

Err.Clear 
GoTo CleanUp 

và:

Resume CleanUp 

KHÔNG BAO GIỜ sử dụng hình thức đầu tiên, luôn luôn sử dụng Resume CleanUp (chỉ). Tiếp tục thực hiện RESET của trạng thái lỗi VB6 nội bộ, do đó khi xảy ra lỗi KHÁC, "Trên nhãn GoTo Error" sẽ được áp dụng. Tôi bạn sử dụng "Err.Clear" thì đối tượng Err bị xóa, nhưng trạng thái lỗi nội bộ KHÔNG được xóa và khi một lỗi khác xuất hiện, nó được coi là mã KHÔNG có bất kỳ trình xử lý ngoại lệ nào và ném ra ngoài hàm. Bạn không thể sửa chữa nó bằng cách sử dụng "On Error GoTo Label2"

Hãy xem xét đoạn mã này: "ERROR"

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 

Nếu bạn chạy này, nó sẽ làm gián đoạn trên hàng. Nếu bạn thay thế "Err.Clear" bằng "Tiếp tục L0" thì việc thực hiện không bị gián đoạn trên "L ERI!" dòng và mã nhảy tới nhãn "L2" và cung cấp "MsgBox Err"

Các vấn đề liên quan