Reflection and Nullables

  • Thread starter Thread starter Joe Bloggs
  • Start date Start date
J

Joe Bloggs

Hi,

Can someone please kindly show me how to determine if a type (read
value
type) is Nullable.

MSDN has this KB:
How to: Identify a Nullable Type (C# Programming Guide)
http://msdn2.microsoft.com/en-us/library/ms366789.aspx

however, using their code snippet, I couldn't get it to work:

public class MyClass
{
public static void Main()
{
Nullable<int> j = new Nullable<int>(20);
Type type = j.GetType();
if (type.IsGenericType && type.GetGenericTypeDefinition() ==
typeof(Nullable<>))
{
Console.WriteLine("j is Nullable");
}
else
Console.WriteLine("j is NOT Nullable");

Console.WriteLine("Type of j is {0}", j.GetType());
}
}

The Output I got is:

j is NOT Nullable
Type of j is System.Int32

thus, is there no way to determine a nullable or an non-nullable value

types?

Thanks for your help in advanced.
 
Joe said:
Hi,

Can someone please kindly show me how to determine if a type (read
value
type) is Nullable.

MSDN has this KB:
How to: Identify a Nullable Type (C# Programming Guide)
http://msdn2.microsoft.com/en-us/library/ms366789.aspx

however, using their code snippet, I couldn't get it to work:

That very page includes the following text:....
if you attempt to obtain type information from Nullable variables at
runtime using the GetType method or the is operator, the result is a
Type object that represents the underlying type, not the Nullable type
itself.
....
GetType always returns a Type object that represents the underlying
type, not the Nullable type.
....

int? i = 5;
Type t = i.GetType();
Console.WriteLine(t.FullName); //"System.Int32"
....
Remember that this code [the test you reproduce below] ****always
returns false if the Type object was returned from a call to
GetType****
public class MyClass
{
public static void Main()
{
Nullable<int> j = new Nullable<int>(20);
Type type = j.GetType();

So this will be the underlying type.
if (type.IsGenericType && type.GetGenericTypeDefinition() ==
typeof(Nullable<>))
{
Console.WriteLine("j is Nullable");
}
else
Console.WriteLine("j is NOT Nullable");

Console.WriteLine("Type of j is {0}", j.GetType());
}
}

The Output I got is:

j is NOT Nullable
Type of j is System.Int32

thus, is there no way to determine a nullable or an non-nullable value
types?

There is, and you have it, but it doesn't work if you get those types
"from Nullable variables at runtime using the GetType method or the is
operator".
 
Ok,

Does that mean that there is no way to use reflection to introspect a
variable if it is a Nullable type? I don't remember any other methods
other than GetType() from retriving the Type from a variable.

Any suggestions?


Larry said:
Joe said:
Hi,

Can someone please kindly show me how to determine if a type (read
value
type) is Nullable.

MSDN has this KB:
How to: Identify a Nullable Type (C# Programming Guide)
http://msdn2.microsoft.com/en-us/library/ms366789.aspx

however, using their code snippet, I couldn't get it to work:

That very page includes the following text:...
if you attempt to obtain type information from Nullable variables at
runtime using the GetType method or the is operator, the result is a
Type object that represents the underlying type, not the Nullable type
itself.
...
GetType always returns a Type object that represents the underlying
type, not the Nullable type.
...

int? i = 5;
Type t = i.GetType();
Console.WriteLine(t.FullName); //"System.Int32"
...
Remember that this code [the test you reproduce below] ****always
returns false if the Type object was returned from a call to
GetType****
public class MyClass
{
public static void Main()
{
Nullable<int> j = new Nullable<int>(20);
Type type = j.GetType();

So this will be the underlying type.
if (type.IsGenericType && type.GetGenericTypeDefinition() ==
typeof(Nullable<>))
{
Console.WriteLine("j is Nullable");
}
else
Console.WriteLine("j is NOT Nullable");

Console.WriteLine("Type of j is {0}", j.GetType());
}
}

The Output I got is:

j is NOT Nullable
Type of j is System.Int32

thus, is there no way to determine a nullable or an non-nullable value
types?

There is, and you have it, but it doesn't work if you get those types
"from Nullable variables at runtime using the GetType method or the is
operator".
 
Joe said:
Does that mean that there is no way to use reflection to introspect a
variable if it is a Nullable type? I don't remember any other methods
other than GetType() from retriving the Type from a variable.

For a local variable, maybe not. (Though why you would need to use
Reflection to tell if a local - that you declared! - is a nullable
type is beyond me.) However, in the much more understandable case
where you need to tell if a particular field (or property, or method
result) in a particular type is nullable, you CAN use Reflection.

For example, this prints True twice:

using System;
using System.Collections.Generic;
using System.Text;

namespace DetectNullableType
{
class Program
{
static void Main(string[] args)
{
Type Class = typeof(Demo);

IsNullable(Class.GetField("Field").FieldType);
IsNullable(Class.GetMethod("Method").ReturnType);

Console.ReadLine();
}

static void IsNullable(Type T)
{
Console.WriteLine(T.IsGenericType &&
T.GetGenericTypeDefinition() == typeof(Nullable<>));
}
}

class Demo
{
public int? Field;
public bool? Method() { return null; }
}
}
 
Joe Bloggs said:
Can someone please kindly show me how to determine if a type (read
value
type) is Nullable.

I also answered in your multipost in dotnet.general

-- Barry
 
Joe Bloggs said:
Does that mean that there is no way to use reflection to introspect a
variable if it is a Nullable type? I don't remember any other methods
other than GetType() from retriving the Type from a variable.

If the variable is the value of a field, you can use
FieldInfo.FieldType. If it's a local, you can use typeof(int?) or
whatever the declared type is. You could use generic type parameter
inference to get what you want:

---8<---
using System;

class App
{
static void Main()
{
int? x = 0;
Console.WriteLine(GetType(x).FullName);
}

static Type GetType<T>(T value)
{
return typeof(T);
}
}
--->8---

This will print:

System.Nullable`1[[System.Int32, mscorlib, Version=2.0.0.0,
Culture=neutral, PublicKeyToken=b77a5c561934e089]]

-- Barry
 
Back
Top