Using "Is" with objects of different types.

rbulph

Junior Contributor
Joined
Feb 17, 2003
Messages
397
If I use "TypeOf" on an object comparing it to a type that it can never be, I get the error "Expression of type [ ]can never be of type [ ]." That's useful. But if I use "Is" to compare one object against another which is of a type that the first can never be, I don't even get a warning. That's led to a few mistakes, and it would be really helpful if I did get some sort of warning. Is there any alternative to creating a function like "StrongIs" below if I want to get some notice of this sort of mistake?

Code:
Public Class Form1

    Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
        Dim x As Button = Me.Button1

        If TypeOf x Is Form Then Beep() 'gives an error
        If x Is Me Then Beep() 'why can't this give an error? 
        If StrongIs(x, Me) Then Beep() 'Is there any alternative to this?
    End Sub

    Friend Function StrongIs(ByVal a As Object, ByVal b As Object) As Boolean
        If a.GetType Is b.GetType Then
            Return a Is b
        Else
            Err.Raise(1)
        End If

    End Function

End Class
 
I must admit I rarely use either operator - normally I 'm not writing code that is dependant on the object type and as such rarely need to compare the types like that.

On the odd occasion I may check to see that two parameters aren't the same actual object but if they are then the type of object(s) are pretty irrelevant to the overall decision.

Out of interest what kind of use are you having for this?
 
I have 545 occurences of the word "Is" in my project! Probably most are the operator (i.e. not in comments).

I have, as an example, a facility for the user to draw a line from one control to another of the same type, using the mouse. If the control that he starts drawing from Is the one that the cursor moves over, then I don't want the line to be drawn. Otherwise I do.
 
I think that

Code:
       If a.GetType.IsAssignableFrom(b.GetType) Or b.GetType.IsAssignableFrom(a.GetType) Then

would be better to use instead of

Code:
If a.GetType Is b.GetType Then

so as to allow for inheritance.
 
It might be easier to define a standard interface that all these 'connectable' objects implement, that way you can be sure that you are working with the correct class of object regardless of it's underlying type.
 
Possibly. Actually I don't think this is going to work, because there are problems with inheritance. Suppose I have a class "Base", and two classes that inherit directly from that, "Derived1" and "Derived2". If I have two references, x and y to Base class objects, it would be perfectly reasonable to have code to check whether x is y. But if x is in fact a Derived1 object and y a Derived2 object and I send them both to a procedure to check whether the comparison is appropriate, it will look as if it's not, because neither of them inherits from the other. I need a comparison of the types with which x and y are declared, not the types which the objects they refer to are. And I don't see how that can be done.

Incidentally, is there a practical difference between Object.ReferenceEquals and Is?
 
If you compare the msil then 'Is' does a bit of work but ultimately just calls Object.ReferenceEquals anyway.

If you are comparing identity (two variables pointing to the same object) then inheritance and interfaces shouldn't make a difference. If the two objects derive from a common base but are of different types then the Is operator will return false. If they are of the same type then the comparison may be true or false depending on if they really point to the same object or not.

If you really wanted to enforce the check being between two variable then you could always create a generic function and require both parameters to be of the same type.
 
Back
Top