为什么在VBA中引发用户定义的错误时需要使用vbObjectError常量?

时间:2019-05-08 12:14:09

标签: excel vba

  

Microsoft Visual Basic for Applications 7.1; 1088版


我通过遵循在线教程创建了一个自定义错误处理程序,并且已经使用了大约一年了,但是我仍然没有得到vbObjectError常数添加到513-65535之间的数字的部分,保留给用户定义的错误。大多数教程建议以Err.Raise vbOjectError + 1000为例来生成自定义错误。这样做的原因是为了避免与错误0-512重叠,这是为系统错误保留的。如果我必须围绕该想法编写代码,则代码应如下所示:

Option Explicit

Sub raiseError()

    On Error GoTo errorHandler

    Dim x As Double
    Dim y As Double

    Let x = 4.8
    Let y = 5.5

    If x <> y Then
        Err.Raise vbObjectError + 1000
    End If

errorHandler:

    Select Case Err.Number
        Case vbEmpty
            MsgBox "alright!"

        Case vbObjectError + 1000
            MsgBox ("User-defined error '" & Err.Number & "':" & _
            vbNewLine & _
            vbNewLine & _
            "X is not equal to Y")

        Case Is <> vbObjectError + 1000
            MsgBox "All other errors"

    End Select

End Sub

现在,从此documentation引用Microsoft:

“ Visual Basic错误(Visual Basic定义的错误和用户定义的错误)在0–65535的范围内。0–512的范围保留用于系统错误; 513–65535的范围适用于用户定义的错误

在类模块中将Number属性设置为自己的错误代码时,请将错误代码号添加到vbObjectError常量。例如,要生成错误号513,请将vbObjectError + 513分配给Number属性。“

但是令我困惑的是vbObjectError常量的值为-2147221504。如您所见,如果您运行代码,vbObjectError1000的总和或513–65535之间的任何数字都远离范围513–65535,该范围可用于用户定义的错误根据微软的说法。

如果我需要使用513–65535范围内的错误编号,为什么不直接使用Err.Raise 513Err.Raise 1000这样的错误编号?

我真的很感谢你们的任何澄清。非常感谢大家。

2 个答案:

答案 0 :(得分:0)

因为没有人回答,所以我会冒一个(希望有教养的)猜测。生成的“错误号”实际上不是介于0到65535(2 ^ 16-1)之间的错误号。这些数字是会产生负错误代码的错误偏移量。

例如,在Access中,您经常会看到正错误号(如果无法连接到DAO工作区,则为3146)。我不会称这些“用户错误”,但是它们不在“系统错误”范围内。

此外,如果真正的错误号不能大于65535(最大的带符号16位数字),则不需要Long类型即可容纳它们。

最后,如果您曾经注意到Microsoft产品显示的一些错误代码,则会看到十六进制代码“ 8xxxxxxx”,它们是带符号十进制的大负数,就好像它们将vbObjectError添加到了自己的内部错误号中一样

因此,在513和65535之间的错误消息是非常方便的数字,您可以使用它们通过添加到vbObjectError来创建错误代码。我想这也使创建存储错误信息(错误号,描述,帮助ID等)的类型以及创建这些类型的数组变得更加容易。例如,Errors(0)将返回错误号为513的类型以及ERR.Raise语句中可能需要的其他信息。

但是为什么vbObjectError等于-2147221504?我不知道。不是-(2 ^ 31)+512。十六进制为FFFFFFFF80040000。我猜你将不得不问微软。

有关更多信息,这是另一个网站对此的看法:http://www.vbforums.com/showthread.php?570075-vbObjectError-what-is-it-for

答案 1 :(得分:0)

我终于找到了一个很好的答案。 Microsoft Err.Number的文档对此进行了很好的解释并提供了以下示例:

' Using Number property with an error from an 
' Automation object
Dim MyError, Msg
' First, strip off the constant added by the object to indicate one
' of its own errors.
MyError = Err.Number - vbObjectError
' If you subtract the vbObjectError constant, and the number is still 
' in the range 0-65,535, it is an object-defined error code.
If MyError > 0 And MyError < 65535 Then
    Msg = "The object you accessed assigned this number to the error: " _
             & MyError & ". The originator of the error was: " _
            & Err.Source & ". Press F1 to see originator's Help topic."
' Otherwise it is a Visual Basic error number.
Else
    Msg = "This error (# " & Err.Number & ") is a Visual Basic error" & _
            " number. Press Help button or F1 for the Visual Basic Help" _
            & " topic for this error."
End If
    MsgBox Msg, , "Object Error", Err.HelpFile, Err.HelpContext

关键是您应该从Err.Number中减去较大的负数,然后对结果进行Select Case。 0-65535表示错误是由Err.Raise生成的。