Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to do constructor chaining in C#

People also ask

How is constructor chaining performed?

Constructor chaining can be done in two ways: Within same class: It can be done using this() keyword for constructors in the same class. From base class: by using super() keyword to call the constructor from the base class.

Why do we chain constructors in C#?

Constructor Chaining is an approach where a constructor calls another constructor in the same or base class. Even though the above approach solves our problem, it duplicates code. (We are assigning a value to ' _id ' in all our constructors). This is where constructor chaining is very useful.

What does this () mean in constructor chaining?

Java Constructor Chaining in the Same Class You can create multiple constructors in the same class, each with a different number of arguments that it accepts. To call one of the constructors in another constructor (of the same class), use the keyword this().

How do you call one constructor from another in C#?

To call one constructor from another within the same class (for the same object instance), C# uses a colon followed by the this keyword, followed by the parameter list on the callee constructor's declaration. In this case, the constructor that takes all three parameters calls the constructor that takes two parameters.


You use standard syntax (using this like a method) to pick the overload, inside the class:

class Foo 
{
    private int id;
    private string name;

    public Foo() : this(0, "") 
    {
    }

    public Foo(int id, string name) 
    {
        this.id = id;
        this.name = name;
    }

    public Foo(int id) : this(id, "") 
    {
    }

    public Foo(string name) : this(0, name) 
    {
    }
}

then:

Foo a = new Foo(), b = new Foo(456,"def"), c = new Foo(123), d = new Foo("abc");

Note also:

  • you can chain to constructors on the base-type using base(...)
  • you can put extra code into each constructor
  • the default (if you don't specify anything) is base()

For "why?":

  • code reduction (always a good thing)
  • necessary to call a non-default base-constructor, for example:

    SomeBaseType(int id) : base(id) {...}
    

Note that you can also use object initializers in a similar way, though (without needing to write anything):

SomeType x = new SomeType(), y = new SomeType { Key = "abc" },
         z = new SomeType { DoB = DateTime.Today };

I just want to bring up a valid point to anyone searching for this. If you are going to work with .NET versions before 4.0 (VS2010), please be advised that you have to create constructor chains as shown above.

However, if you're staying in 4.0, I have good news. You can now have a single constructor with optional arguments! I'll simplify the Foo class example:

class Foo {
  private int id;
  private string name;

  public Foo(int id = 0, string name = "") {
    this.id = id;
    this.name = name;
  }
}

class Main() {
  // Foo Int:
  Foo myFooOne = new Foo(12);
  // Foo String:
  Foo myFooTwo = new Foo(name:"Timothy");
  // Foo Both:
  Foo myFooThree = new Foo(13, name:"Monkey");
}

When you implement the constructor, you can use the optional arguments since defaults have been set.

I hope you enjoyed this lesson! I just can't believe that developers have been complaining about construct chaining and not being able to use default optional arguments since 2004/2005! Now it has taken SO long in the development world, that developers are afraid of using it because it won't be backwards compatible.


This is best illustrated with an example. Imaging we have a class Person

public Person(string name) : this(name, string.Empty)
{
}

public Person(string name, string address) : this(name, address, string.Empty)
{
}

public Person(string name, string address, string postcode)
{
    this.Name = name;
    this.Address = address;
    this.Postcode = postcode;
}

So here we have a constructor which sets some properties, and uses constructor chaining to allow you to create the object with just a name, or just a name and address. If you create an instance with just a name this will send a default value, string.Empty through to the name and address, which then sends a default value for Postcode through to the final constructor.

In doing so you're reducing the amount of code you've written. Only one constructor actually has code in it, you're not repeating yourself, so, for example, if you change Name from a property to an internal field you need only change one constructor - if you'd set that property in all three constructors that would be three places to change it.


What is usage of "Constructor Chain"?
You use it for calling one constructor from another constructor.

How can implement "Constructor Chain"?
Use ": this (yourProperties)" keyword after definition of constructor. for example:

Class MyBillClass
{
    private DateTime requestDate;
    private int requestCount;

    public MyBillClass()
    {
        /// ===== we naming "a" constructor ===== ///
        requestDate = DateTime.Now;
    }
    public MyBillClass(int inputCount) : this()
    {
        /// ===== we naming "b" constructor ===== ///
        /// ===== This method is "Chained Method" ===== ///
        this.requestCount= inputCount;
    }
}

Why is it useful?
Important reason is reduce coding, and prevention of duplicate code. such as repeated code for initializing property Suppose some property in class must be initialized with specific value (In our sample, requestDate). And class have 2 or more constructor. Without "Constructor Chain", you must repeat initializaion code in all constractors of class.

How it work? (Or, What is execution sequence in "Constructor Chain")?
in above example, method "a" will be executed first, and then instruction sequence will return to method "b". In other word, above code is equal with below:

Class MyBillClass
{
    private DateTime requestDate;
    private int requestCount;

    public MyBillClass()
    {
        /// ===== we naming "a" constructor ===== ///
        requestDate = DateTime.Now;
    }
    public MyBillClass(int inputCount) : this()
    {
        /// ===== we naming "b" constructor ===== ///
        // ===== This method is "Chained Method" ===== ///

        /// *** --- > Compiler execute "MyBillClass()" first, And then continue instruction sequence from here
        this.requestCount= inputCount;
    }
}