Question A question on object casting.

mbb

Well-known member
Joined
Jun 3, 2009
Messages
52
Programming Experience
10+
Here is a test program I wrote to explore a facet of object casting ...

VB.NET:
Module Module1

    Sub Main()

        Dim class1 As MyBaseClass = New MyBaseClass()
        Dim class2 As MyInheritedClass = New MyInheritedClass()
        Dim class3 As MyBaseClass = Nothing

        If TypeOf class1 Is MyBaseClass Then
            Console.WriteLine("Class1 is MyBaseClass")
        Else
            Console.WriteLine("Class1 is not MyBaseClass")
        End If

        If TypeOf class1 Is MyInheritedClass Then
            Console.WriteLine("Class1 is MyInheritedClass")
        Else
            Console.WriteLine("Class1 is not MyInheritedClass")
        End If

        If TypeOf class2 Is MyBaseClass Then
            Console.WriteLine("Class2 is MyBaseClass")
        Else
            Console.WriteLine("Class2 is not MyBaseClass")
        End If

        If TypeOf class2 Is MyInheritedClass Then
            Console.WriteLine("Class2 is MyInheritedClass")
        Else
            Console.WriteLine("Class2 is not MyInheritedClass")
        End If

        class3 = TryCast(class2, MyBaseClass)

        If TypeOf class3 Is MyBaseClass Then
            Console.WriteLine("Class3 is MyBaseClass")
        Else
            Console.WriteLine("Class3 is not MyBaseClass")
        End If

        If TypeOf class3 Is MyInheritedClass Then
            Console.WriteLine("Class3 is MyInheritedClass")
        Else
            Console.WriteLine("Class3 is not MyInheritedClass")
        End If

        Console.ReadKey()
    End Sub

End Module

The problem comes with the TryCast statement on class3. My intention is that class3 remains as a baseclass, but when the TryCast is applied, class3 morphs itself into an Inherited class which is not what I wanted.

So is there a gap in my OOP/VB.NET knowledge and this action is legitimate or should class3 still be regarded as a base class?
 
Dim class2 As MyInheritedClass = New MyInheritedClass()
Dim class3 As MyBaseClass = TryCast(class2, MyBaseClass)
class3 variable will here reference a MyInheritedClass instance type casted as MyBaseClass (granted 'inherited' inherits 'base'). If the cast wasn't possible TryCast would return a null reference (Nothing). A type cast doesn't change the object, only what type it is read as. If say your 'base' had a member A and 'inherited' had a member B, then you could only see the A member from your class3 reference. From class2 reference you could see both the inherited A member and the type member B.

The TypeOf operator checks if the object is the exact type you specify, or inherits that type, or implements if the type is interface, all the way up the inheritance chain. Ie, if the object is compatible with that type. To check if the object is exactly that type you can do this:
VB.NET:
If obj.GetType Is GetType(baseclass) Then
Never mind the naming conventions, they are all off here :rolleyes:
 
Great that explains something to me.

So, unlike say C, a cast on an object will not physically change the object. e.g. casting a char into an int gives you an int.

In OOP, casting object A into object B, gives you object A with different behaviour. What about non-reference types in .NET?

So I am still left with having to instantiate the object I want and explictly setting the properties? Is there a better way than this:

VB.NET:
Function MyCast(pSource as InheritedClass) as BaseClass

    Dim result as BaseClass()  = new BaseClass()

    result.id = pSource.id
    result.otherproperty = pSource.otherproperty

    return result
end function

This, BTW is related to this thread:

http://www.vbdotnetforums.com/linq/34808-linq-short-comings.html#post102691
 
That is different from TryCast, which only operates on reference types. Converting a value type with CType/DirectCast operators or a conversion function like CInt will in fact convert the value of one type to a value of a different type, when a widening or narrowing conversion is defined between those types. You can use those operators with reference types also, but unlike the Try version they will throw an exception if the cast is not valid.
 
I'll test CType and DirectCast again. I'm sure I got the same result as TryCast in my example.

EDIT: No difference with CType or DirectCast.
 
Last edited:
For reference types there is no difference in what type casting does. The only way to convert a reference type object to another type object is through an explicit conversion where you create a new object and configure/copy the data, as you did above. I'm not familiar with the specific problem you have with Linq, but other than inheritance you can also extend types with partial classes, see Partial keyword, this could perhaps be an option.
 
Thanks you have clarified my problem with casting.

I have extended the linq to sql partial class which Linq will use on InsertOnSubmit(). But if you inherit from the extended partial class, Linq won't use it properly, a null exception is raised from the InsertOnSubmit().

Come to think of it could that problem be something to do with applying reflection attributes to the inherited class? Maybe I'll try another test program out to explore this ...
 
Back
Top