0

How do I force all derived classes of an interface to have a constructor with a signature? This doesn't work:

public interface Constructor<T> where T : Constructor<T>, new()
{
    Constructor(T);
}

public interface IParameters
{
}

public interface IRule : Constructor<IParameters>
{
    //IRule (IParameters); must exist
}
Ivan
  • 7,448
  • 14
  • 69
  • 134

3 Answers3

1

You can't, not via an interface. But you can sort of get at it with an abstract class. Similar to what the accepted answer here describes, try:

public abstract class MustInitialize<T>
{
    public MustInitialize(T parameters)
    {

    }
}

public class Rule : MustInitialize<IParameters>, IRule
{
    IParameters _parameters;

    public Rule(IParameters parameters)
        : base (parameters)
    {
        _parameters= parameters;
    }
}
Mark Z.
  • 2,127
  • 16
  • 33
  • This still doesn't enforce the constructor on the derived class to take in parameters. Whatever implementation of `IParameters` can be initialized in the call to the base constructor. – Zohar Peled Jul 16 '19 at 05:49
  • "sort of get at it" @ZoharPeled , and better than nothing! – Mark Z. Jul 16 '19 at 05:55
  • I started to write a comment but it got too long. See my answer - it explains exactly what I mean. – Zohar Peled Jul 16 '19 at 06:20
1

You can't force a specific constructor signature.
Even with an abstract class as demonstrated in Mark's answer, you can only force the constructor of the abstract class, but nothing is stopping the author of the derived class to do something like this:

public class Rule : MustInitialize<IParameters>, IRule
{
    public Rule()
        : base (new Parameters())
    {
        // Assuming Parameters is a class that implements the IParameters interface
    }
}

However, you can force dependency injection by using method (setter) injection:

public interface IMethodInjection<T>
{
    void Method(T injected);
}
Zohar Peled
  • 79,642
  • 10
  • 69
  • 121
0

I think you can design your base class like the following example:

public abstract class MyBase
{
    private MyBase()
    {
    }

    public MyBase(string a)
    {
    }
}

public class MyDerived : MyBase
{
    public MyDerived(string a) : base(a)
    {
    }
}

You can even delete the private constructor if its not needed

Aminul
  • 1,738
  • 2
  • 24
  • 42