1

I'm trying in VB.NET (framework 3.5) obtain the Type of a Nullable Property that has a Nothing value (its default value), to know how make the CType. The code would be something like this:

Class DinamicAsign
Public Property prop As Integer?
Public Property prop2 As Date?

Public Sub New()
    Asign(prop, "1")
    Asign(prop2, "28/05/2013")
End Sub

Public Sub Asign(ByRef container As Object, value As String)
    If (TypeOf (container) Is Nullable(Of Integer)) Then
        container = CType(value, Integer)
    ElseIf (TypeOf (container) Is Nullable(Of Date)) Then
        container = CType(value, Date)
    End If
End Sub
End Class

This code doesn't work correctly. The problem is how to know the type of "container".

If "prop" has a value ("prop" is not nothing) this code works:

If (TypeOf(contenedor) is Integer) then...
If (contenedor.GetType() is Integer) then...

But if the value is nothing I have no idea how to obtain the Type. I've tried this ways, but don't work:

container.GetType() 

TypeOf (contenedor) is Integer 

TypeOf (contenedor) is Nullable(of Integer) 

I know that someone could response that "container" is nothing because is not referencing any object and you can't know the Type. But this seems to be wrong because I have found a trick to solve this: creating a overloaded functions to make the cast, this way:

Class DinamicAsign2
Public Property prop As Integer?
Public Property prop2 As Date?

Public Sub New()
    Asignar(prop, "1")
    Asignar(prop2, "28/05/2013")
End Sub

Public Sub Asignar(ByRef container As Object, value As String)
    AsignAux(container, value)
End Sub

Public Sub AsignAux(ByRef container As Integer, value As String)
    container = CType(value, Integer)
End Sub

Public Sub AsignAux(ByRef container As Decimal, value As String)
    container = CType(value, Decimal)
End Sub
End Class

If "container" Is Integer it will call to

public function AsignAux(byref container as Integer, value as string)

And if "container" Is Date will call to

public function AsignAux(byref container as Date, value as string)

This works right, .NET knows anyway the type of Object because calls to correct overloaded function. So I want to find out (as .NET does) a way to determine the Type of Nullable Object that has a nothing value.

Thx

CarlosTI
  • 133
  • 11

1 Answers1

3

When a Nullable(Of T) becomes an Object, the type data is lost: it either becomes a plain old Nothing, or the type it represents, e.g. Integer. You might be able to change your method to do this:

Public Sub Asign(Of T As Structure)(ByRef container As Nullable(Of T), value As String)
    ' T is Integer or Date, in your examples
    container = System.Convert.ChangeType(value, GetType(T))
End Sub

If not, you'll have to record the type elsewhere, and pass that into your method.

For some info on why the boxing/unboxing was set up to work this way, see Boxing / Unboxing Nullable Types - Why this implementation?. In short, it's the most sensible way to work with a nullable type as an Object.

Community
  • 1
  • 1
Tim S.
  • 55,448
  • 7
  • 96
  • 122
  • Perfect solution, thx very much! Anyway, I think Type is not lost when you use a object parameter, because, as I say in my previous code, if you use overload functions .NET knows which function calls depending on the type of object parameter (ie, depending on the type of nullable property) – CarlosTI Jun 07 '13 at 06:18
  • Hm, interesting, apparently the VB compiler or runtime does some "magic" that C# (which I am more familiar with) does not, which allows your code in `DinamicAsign2` to work. Nullable aside, in C# if you have an `Object` in C# and you try to call `AsignAux` in such a way, it won't resolve. – Tim S. Jun 07 '13 at 11:50
  • If you have a value that was a `Nullable(Of Integer)` that is `Nothing`, and you put it in an `Object` variable, do you see the type such as `Integer` anywhere in the debugger for that `Object`? In C# you would not. However, if you had an `int?` in C# that had a real int value, and you store that in an `object`, it becomes simply an `int` (no longer an `int?`). – Tim S. Jun 07 '13 at 19:12