Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is there a Nullable<T> struct and Nullable class?

Tags:

c#

nullable

There is a Nullable<T> struct and there is also another static Nullable class with three static methods.

My question is, why can't these static methods in static Nullable class go into Nullable<T> struct? What is the reason for defining them in two different types?

And there is a INullable interface as well.What does it do?

like image 627
Prudhvi Avatar asked Feb 06 '23 07:02

Prudhvi


2 Answers

  1. Is a standard practice with Generics to have class with the same name of your generic class with utility methods related to the generic class. Because when you use a generic class you cant't infer the generics in the type declaration you'll end up with many more characters. Look how it would be if the static methods were placed in the generic class:

    Nullable<int?>.Compare(x, Y);
    var n = new Tuple<int,string>(10, "Text");
    

    vs

    Nullable.Compare(x, Y);
    var n = Tuple.Create(10, "Text");
    

    I included Tuple as another example.

  2. Interfaces and base classes are very useful in Generics, and since Nullable<> is struct and structs cannot have a base class, we are left with interfaces. Now here is a possible usage of it.

    {
        int? a = 10;
        long? b = 10L;
    
        Process(a);
        Process(b);
    }
    
    private static void Process(INullable value)
    {
        if (value.IsNull)
        {
            // Process for null .. 
        }
        else
        {
            // Process for value .. 
        }
    }
    
like image 142
AL - Divine Avatar answered Feb 08 '23 17:02

AL - Divine


they are written is a separate class because those methods are utility methods and are intended to be used anywhere without actually having to create a nullable structure instance every time you want to use these methods for example,

public static bool Is<T>(this T variable,Type type) {
    if (var != null) {
        Type currentType = variable.GetType();
        type = Nullable.GetUnderlyingType(type) ?? type;
        while (currentType != typeof(object)) {
            if (currentType == type) {
                return true;
            }
            currentType = currentType.BaseType;
        }
    }                  
    return false;
}

In the above example the variable can be of any type(not necessarily nullable), but it can actually be nullable, and hence has to be checked if nullable.

For that very case I used the Nullable.GetUnderlyingType(type), because it is a utility method.This is intended behaviour for utility methods i.e. making them reusable anywhere required without having to create an instance, every time you need them.

like image 31
Thanesh Davuluri Avatar answered Feb 08 '23 17:02

Thanesh Davuluri