Jeff
Jeff

Reputation: 165

VB .net bc30452 operator = is not defined for types - how to create custom operator

In VB .NET I am getting an error "bc30452 operator = is not defined for types". I tried to create an override but it did not work.

Public Class question
    Public [question] As String
    Public answer As String

    Public Overrides Function Equals(obj As Object) As Boolean
        If obj Is GetType(question) Then
            If (question = CType(obj, question).question) And (answer = CType(obj, question).answer) Then
                Return True
            Else
                Return False
            End If

        End If
        Return False

    End Function
End Class

Upvotes: 1

Views: 2140

Answers (2)

Joel Coehoorn
Joel Coehoorn

Reputation: 416121

You need to override the operator, in addition the Equals() method. A quirk of VB.Net also requires you to overload the <> operator, and a quirk of .Net means you should also override the GetHashCode() method whenever you override Equals().

Public Class Question
    Public Property question As String
    Public Property answer As String

    Public Overrides Function Equals(obj As Object) As Boolean
        Dim o As Question = TryCast(obj, Question)
        Return o IsNot Nothing AndAlso o.question.Equals(Me.question) AndAlso o.Answer.Equals(Me.Answer)
    End Function

    Public Shared Operator =(obj1 as Question, obj2 as Question) As Boolean
         Return obj1 IsNot Nothing AndAlso obj1.Equals(obj2)
    End Operator

    Public Shared Operator <>(obj1 As Question, obj2 As Question) As Boolean
        Return obj1 Is Nothing OrElse Not obj1.Equals(obj2) 
    End Operator

    Public Overrides Function GetHashCode() As Integer
        Return HashCode.Combine(Me.question, Me.answer)
    End Function
End Class

At this point, we've now done most of the work to also implement IEquatable<Question> and IComparable<Question>. It would also be a very good idea to rename either the question property or the Question type, to avoid confusion in the code and potential bugs.

Finally, HashCode.Combine() requires the .Net platform extensions (see NuGet). There are some pitfalls around combining hashcodes from different fields, and using this method makes it easier to avoid them and to do it correctly.

Upvotes: 3

jmcilhinney
jmcilhinney

Reputation: 54457

The problem is that you are using the same name for your type and your field and the identifier is being interpreted as one when you mean the other. Use Me to qualify the field and you should be OK. Better still use different names.

I just tested your code and I didn't see that error message, so I'm not sure what's up at your end. That said, here's a better implementation:

Public Class Question

    Public Property Question As String

    Public Property Answer As String

    Public Overrides Function Equals(obj As Object) As Boolean
        Dim otherQuestion = TryCast(obj, Question)

        Return Question = otherQuestion?.Question AndAlso Answer = otherQuestion?.Answer
    End Function

    Public Overrides Function GetHashCode() As Integer
        Return Question.GetHashCode() Xor Answer.GetHashCode()
    End Function

    Public Shared Operator =(q1 As Question, q2 As Question) As Boolean
        Return q1?.Question = q2?.Question AndAlso q1?.Answer = q2?.Answer
    End Operator

    Public Shared Operator <>(q1 As Question, q2 As Question) As Boolean
        Return q1?.Question <> q2?.Question AndAlso q1?.Answer <> q2?.Answer
    End Operator

End Class

That uses appropriate naming and properties rather than fields. The TryCast method will return a reference of the specified type that refers to the original object if it is that type or Nothing if it isn't. The ?. operator accounts for the fact that the reference maybe Nothing and will evaluate to Nothing if it is.

Upvotes: 1

Related Questions