未为类型“ DBNull”和类型“ DBNull”定义运算符“ =”

时间:2019-03-01 16:22:58

标签: vb.net dbnull

在使用SqlDataReader(即“ reader”)时,尝试检查值是否为DBNull时遇到了以下错误。

  

未为类型'DBNull'和类型'DBNull'定义运算符'='。

使用以下代码时:

If reader("MyColumn") = DBNull.Value Then
  '...
End If

我通过使用对IsDBNull()的调用来解决该错误,我怀疑这是由于'Is'和'='之间的差异所致。

但是,我的问题是:为什么不能使用'='运算符进行比较?

2 个答案:

答案 0 :(得分:1)

在SQL中,null = null的结果为false。这可能就是为什么没有为此类型定义相等运算符的原因。

您无法确定未知的事物是否等于其他未知的事物,从而使等式运算符无用。

使用DBNull.Value.Equals()确定是否为空。

答案 1 :(得分:1)

并非所有类型都可与=运算符一起使用。当一个类型定义了应该如何使用各种运算符的逻辑时,它称为“运算符重载”(由于它与方法重载无关,并且有很大的不同,因此它有点令人困惑)。基本Object类型不会重载=运算符,因此,当您创建自定义类时,它不会从=继承Object运算符重载。因此,只有那些特别使操作员超负荷的类型才能实际使用它。例如,以下代码将无法编译:

Module Module1
    Public Sub Main()
        Dim dan As New Person() With {.Id = 1, .Name = "Daniel Thorne"}
        Dim steve As New Person() With {.Id = 2, .Name = "Steven Doggart"}
        If dan = steve Then
            Console.WriteLine("They're the same")
        End If
    End Sub

    Public Class Person
        Public Property Id As Integer
        Public Property Name As String
    End Class
End Module

编译器给出以下构建错误:

  

未为类型'Module1.Person'和'Module1.Person'定义BC30452运算符'='。

但是,它会按预期构建并运行:

Public Sub Main()
    Dim dan As New Person() With {.Id = 1, .Name = "Daniel Thorne"}
    Dim steve As New Person() With {.Id = 2, .Name = "Steven Doggart"}
    If dan = steve Then
        Console.WriteLine("They're the same")
    End If
End Sub

Public Class Person
    Public Property Id As Integer
    Public Property Name As String

    Public Shared Operator =(x As Person, y As Person) As Boolean
        Return AreEqual(x, y)
    End Operator

    Public Shared Operator <>(x As Person, y As Person) As Boolean
        Return Not AreEqual(x, y)
    End Operator

    Private Shared Function AreEqual(x As Person, y As Person) As Boolean
        If (x Is Nothing) And (y Is Nothing) Then
            Return True
        ElseIf (x IsNot Nothing) And (y IsNot Nothing) Then
            Return x.Id = y.Id
        Else
            Return False
        End If
    End Function
End Class

所以,您在DBNull上收到此错误的原因是,出于任何原因,编写该类的开发人员都选择不为其重载=运算符。至于为什么,你猜我和我一样好。

请注意,您也可以重载许多其他运算符,这有时会很有用。但是,要小心。如果您对运算符重载的使用过于宽容,您可能会后悔。