10

Is it good to have a constructor in abstract class?

is it a good programming practice to create constructor of abstract class? since abstract classes can not be initialized, their child classes are initialized.

Following is my class structure.

public abstract class Scheduler
{
    private Storyboard timer;

    protected Scheduler()
    {
        // initialize the timer here.
        timer = new Storyboard();

        this.PollInterval = 60;
    }
}


public class TaskScheduler : Scheduler
{
    public TaskScheduler()
        : base()
    {

    }
}
Zain Shaikh
  • 5,833
  • 6
  • 35
  • 64

4 Answers4

13

Yes, it's absolutely fine. Just because the constructor can only be called by derived classes doesn't mean it won't be useful. For example, you might have an abstract class which represents a named entity of some kind - it would make sense to take the name as a constructor parameter.

It would probably be worth making the constructor protected, to make it even more obvious that you can't just call it from elsewhere.

Note that there being a constructor (or multiple constructors) in an abstract class does force derived class constructors to go through it, but it doesn't force the derived classes to have the same constructor signatures. For example:

public abstract class NamedFoo
{
    private readonly string name;
    public string Name { get { return name; } }

    protected NamedFoo(string name)
    {
        this.name = name;
    }
}

public class DerivedFooWithConstantName
{
    public DerivedFooWithConstantName() : base("constant name")
    {
    }
}

In this case the derived class constructor is "removing" a parameter (by providing a constant value as the argument to the abstract class constructor) but in other cases it could "add" parameters that it required, or have a mixture.

Jon Skeet
  • 1,261,211
  • 792
  • 8,724
  • 8,929
  • @JonSkeet sorry to necromance a post from 2010 but the OP had no params in their base constructor, it's worth mentioning that calling `:base()` in a derived class is redundant if the only ctor in the base class is the default one (because it gets called anyway). I have a concern about "hiding" the need for the ctor parameters, say the base class requires a `IMagicWand`, there's no way for the derived class to know of that requirement until the compiler complains about it - *that's* my problem with protected constructors in abstract classes... or am I over-thinking this? – Mathieu Guindon Apr 13 '13 at 17:25
5

There is absolutely no reason not to have a constructor in an abstract base class.

The abstract class is initialized and works just like any other class. The abstract keywords only do the following:

  • It prevents the class itself to be instantiated directly. It can only be instantiated by instantiating an inherited class. This does not change the behavior of initialization compared to a not abstract base class;

  • It allows you to have abstract methods, properties and events in the class.

If you e.g. do not have abstract methods, properties or events, exactly the same result can be accomplished by making the constructor of a class protected (like you did). This also prevents the class to be instantiated directly. The behavior does not change however compared to an abstract class.

The primary difference then becomes the ability to declare methods, properties and events as abstract which you can only do when the class is marked abstract.

Pieter van Ginkel
  • 27,926
  • 8
  • 67
  • 103
1

Having constructor in abstract class can be useful at times. This question is a duplicate, and dealt great deal in an related post. Even though it specifically reference JAVA, conceptually it applies to C# also.

Can an abstract class have a constructor?

Community
  • 1
  • 1
kuriouscoder
  • 4,928
  • 6
  • 23
  • 38
0

Constructors on abstract types can be called only by derived types. Because public constructors create instances of a type, and you cannot create instances of an abstract type, an abstract type that has a public constructor is incorrectly designed. CA1012: Abstract types should not have constructors

Fix the violation by changing the accessibility of the constructor from public to protected.

Example:

namespace Sample  
{        
    public abstract class Book      
    {          
        protected Book()           
        {          
        }      
    } 
} 
Chef_Code
  • 241
  • 3
  • 11