65.9K
CodeProject is changing. Read more.
Home

Default(T)

Sep 24, 2017

CPOL

1 min read

viewsIcon

13582

downloadIcon

28

Use and examples for the keyword Default in generics

Introduction

Default represents default value of T parameter in generics instructions. In several cases, the default keyword is an absolute unknown and we think it’s unnecessary or its functionality is null. There are some development moments with the generics classes where default keyword can be useful.

Default keyword can make our work easier and it may make the code safer.

Default(T)

This keyword returns the default value of type parameter.

These are the default values for the more important types inside of CLR:

  • Classes -> null.
  • Nullable<T> -> null.
  • Numerics structs (int, double, decimal, etc) -> 0.
  • DateTime structs -> 01/01/0001.
  • Char structs -> empty char.
  • Bool structs -> false.

Evaluation Initializes T Parameters

This is a very simple generic method example. This method has two ref parameters of T type and changes your values in the implementation.

public static void ChangeValues<T>(ref T a, ref T b)
{
    T _a = a;
    T _b = b;

    a = _b;
    b = _a;
}

The ChangeValues method hasn’t generic restriction filter so that T will be any type (reference type or value type)

If necessary, validate if the parameters have been initialized (has a valid value different to initialize value), add a validation chunk:

public static void ChangeValues<T>(ref T a, ref T b)
{
    if(a.Equals(null) || b.Equals(null))
    {
        throw new ArgumentException("....");
    }

    T _a = a;
    T _b = b;

    a = _b;
    b = _a;
}

We have a problem, because this implementation doesn’t verify the default value types.

It will be a wrong execution:

static void Main(string[] args)
{
    DateTime a = new DateTime();  // bad value
    DateTime b = DateTime.Today;

    System.Console.WriteLine($"a --> {a}");
    System.Console.WriteLine($"b --> {b}");

    System.Console.WriteLine();

    ChangeValues(ref a, ref b);

    System.Console.WriteLine($"a --> {a}");
    System.Console.WriteLine($"b --> {b}");

    System.Console.Read();
}

Console output:

To correct this bug, we will a new method version with the default keyword inclusion:

public static void NewChangeValues<T>(ref T a, ref T b)
{

    if (a.Equals(default(T)) || b.Equals(default(T)))
    {
        throw new ArgumentException("....");
    }

    T _a = a;
    T _b = b;

    a = _b;
    b = _a;
}

Create Empty Instance

Another example could be the possibility to create empty instance of T types without reflection (Activator).

public T  CreateEmptyInstace<T>(T item)
{
    //var result = Activator.CreateInstance<T>(); à Expression
    var result = default(T);

    return result;
}

Reset Generics Instances

Another use case for Default(T) could be for reset instance of generics objects.

public void ResetValue<T>(ref T item)
{
    item = default(T);
}