1

Is there any way to enforce a specific constructor in Java classes?

For example I want all classes that inherit from a Class to have a constructor like -

public classname(string s1,string s2){....}

I know it should not be avoided because it can lead to problems with multiple inheritance. But is there a way to do it anyway?

Reg
  • 10,717
  • 6
  • 37
  • 54
ju ho
  • 318
  • 1
  • 17
  • 10
    Simply: no. Sorry. – Alex Salauyou Aug 19 '15 at 12:39
  • "_I know it should not be done_" They why do it? Why on earth would you practice doing things the wrong way? – takendarkk Aug 19 '15 at 12:40
  • Constructors cannot be overridden. It is to create instance of class. – Nitesh Virani Aug 19 '15 at 12:41
  • possible duplicate of [How do you force constructor signatures and static methods?](http://stackoverflow.com/questions/161231/how-do-you-force-constructor-signatures-and-static-methods) – Alex Salauyou Aug 19 '15 at 12:41
  • _"I know it should not be avoided because it can lead to problems with multiple inheritance."_ Well, java doesn't support multiple inheritance. – BackSlash Aug 19 '15 at 12:41
  • 1
    @BackSlash Not exactly. It supports multiple inheritance of contract, not of implementation. – RealSkeptic Aug 19 '15 at 12:42
  • 2
    @ju ho: why do you need it? – Lyubomyr Shaydariv Aug 19 '15 at 12:43
  • if you have a custom constructor and no no-arg constructor in your super class your subclasses must implement at least a super() call to it as the implicit super() call would lead to a compiler error. Its really no good practise though. – dly Aug 19 '15 at 12:45
  • I need it because I load classes at runtime with the reflection API and I want all the classes I load to have a specific constructor. All the classes I load inherit from another class so i was wondering if I can just enforce it. – ju ho Aug 19 '15 at 12:46
  • 1
    @juho all you can do here is to check presence of constructor with required signature when loading these classes. – Alex Salauyou Aug 19 '15 at 12:54
  • @juho Ok, got it. Maybe the factory design pattern can be helpful for you? This may help getting rid of the reflection API too. – Lyubomyr Shaydariv Aug 19 '15 at 13:21

3 Answers3

4

There are no facilities in Java to do that directly.

However, it can be enforced to some extent usin an abstract method.

abstract class Base {

    Base(String s1, String s2) {
        init(s1, s2);
    }

    protected abstract void init(String s1, String s2);
}

class MyClass extends Base {

    // Forced to do this.
    MyClass() {
        super("One", "Two");
    }

    // Forced to do this.
    @Override
    protected void init(String s1, String s2) {
    }

}
OldCurmudgeon
  • 64,482
  • 16
  • 119
  • 213
3

You want that there is only one constructor, and that with the same signature. That could in a costly way done with reflection, at run-time.

public BaseClass(String s, String t, int n) {
    Class<?> cl = getClass();
    do {
        check(cl);
        cl = cl.getSuperclass();
    } while (cl != BaseClass.class);
}

private void check(Class<?> cl) {
    if (cl.getConstructors().length != 1) {
        throw new IllegalStateException("Needs only 1 constructor in: " + cl.getName());
    }
    try {
        cl.getConstructor(String.class, String.class, int.class);
    } catch (NoSuchMethodException e) {
        throw new IllegalStateException("Constructor should have parameter types (String, String, int) in: " + cl.getName());
    }
}

Not advisable

However you could make a factory to be used that hides class hierarchies. Or in fact use a single class that delegates to your class hierarchy (has a member of your class).

Joop Eggen
  • 107,315
  • 7
  • 83
  • 138
-1

Sorry, but no, you cannot force classes to only implement a specific constructor.

Keith
  • 3,079
  • 2
  • 17
  • 26
  • Yes you can. Make an abstract class with a protected constructor. Everything which is an implementation of that class must call the constructor – Mark Aug 19 '15 at 13:18
  • 2
    @Mark must call, but must not have the same constructor. – Alex Salauyou Aug 19 '15 at 13:20
  • Oops -- I missed an operative word "... to *only* implement..." in my response response. Thanks for catching that. :) – Keith Aug 19 '15 at 13:20
  • @SashaSalauyou I get what he's saying. We're probably debating semantics of my poorly worded answer Yes, you must define an explicit constructor, at least by calling super(...) in the child class – Keith Aug 19 '15 at 13:23
  • That's what I meant. With the abstract method you must define a constructor but indeed your implementing class could implement its own however it likes. – Mark Aug 19 '15 at 15:25