0

Is something like this possible

abstract class AbstractSuperClass {
  private Entity entity;

  public AbstractSuperClass(Entity entity) {
    this.entity = entity;
  }

  public abstract void operate();
}

public class SubClass extends AbstractSuperClass {
  public void operate() {
    this.entity.doVoidMethod(); // is this.entity defined in instances of SubClass ?
  }
}

// ... somewhere else

Entity instantiatedEntity = new Entity();
SubClass instance = new SubClass(instantiatedEntity);
instance.operate(); // does this call this.entity.doVoidMethod() inside of instance?

I want to be able to skip writing my own constructors in subclasses of an abstract class I'm writing. All of the constructors would be identical in every subclass.

If I skip writing a constructor for a subclass of an abstract class (is this even allowed?) does the abstract class' constructor get used by default?

theonlygusti
  • 11,032
  • 11
  • 64
  • 119
  • Only if it has no arguments and is accessible. – user207421 Apr 06 '18 at 11:21
  • @EJP What do you mean by "accessible"? And the constructor has to have one argument – theonlygusti Apr 06 '18 at 11:30
  • Normal Java source code needs to include a constructor for every subclass that calls the `super` constructor passing it an `Entity`. However, you may be able to have this generated automatically using annotations, similar to those of Lombok. – DodgyCodeException Apr 06 '18 at 11:34
  • @DodgyCodeException how do I use annotations to do this? (I've not heard of Lombok) – theonlygusti Apr 06 '18 at 11:36
  • This is something that can't be answered in a reply to a comment. There are whole books written about how to do this. – DodgyCodeException Apr 06 '18 at 11:37
  • @DodgyCodeException Not necessary for the default constructor. – lexicore Apr 06 '18 at 11:38
  • See also: https://stackoverflow.com/questions/1644317/java-constructor-inheritance – lexicore Apr 06 '18 at 11:39
  • An abstract class still have a constructor, it just can't be call directly to instantiate the instance. So if you don't define one, a default constructor will be adding at compile time that will do call `super()`. Here, you don't have one so it will not compile. You can't do much about this. – AxelH Apr 06 '18 at 11:40
  • @lexicore I wasn't talking about default constructors, but something like an `@DuplicateAllNonDefaultSuperclassConstructors` annotation that generates non-default constructors in the annotated class which directly pass their arguments to the analogous `super(...)` constructor. – DodgyCodeException Apr 06 '18 at 12:16

4 Answers4

1

First of all, if you don't define constructors, a default one with no argument is considered.
In other words, if you want to use new SubClass(instantiatedEntity); you must define the constructor within the SubClass that takes a single argument of type Entity.
In other words, you cannot skip writing your own constructors in case you want to pass a parameter.

Secondly, within your SubClass, you cannot call this.entity.doVoidMethod();. This because the entity attribute is private within the base class and therefore not accessible by the SubClass.

Furthermore, within AbstractSuperClass you defined public abstract Operate();. You probably meant public abstract void operate();. There's a similar mistake in the SubClass.

Robert Kock
  • 5,795
  • 1
  • 12
  • 20
1

I want to be able to skip writing my own constructors in subclasses of an abstract class I'm writing. All of the constructors would be identical in every subclass.

You can't. Constructors are not inherited in Java:

Java Constructor Inheritance

The only quasi-exception is the default constructor. However it is strictly speaking not inheritance. If there are no constructors, the default one is added and it will call super().

If I skip writing a constructor for a subclass of an abstract class (is this even allowed?) does the abstract class' constructor get used by default?

No. Constructors of superclass are neither inherited nor copied.

lexicore
  • 42,748
  • 17
  • 132
  • 221
  • The default constructor idea is useful to not be forced to define constructor, so could be a partial answer IF the parent class have a constructor with no parameter. But that's a restricted solution. – AxelH Apr 06 '18 at 11:57
-1

According to your code above, you are using subclass is extending from an abstract class.

abstract class A{
 A(){
  //todo: some work
 }
 abstract methodA();
 methodB(){
  //todo:something: implementation within the abstract class.
 }
}
class B extends A{
 B(){
 super(this);
  }

}

I believe to use abstract constructor you would use the super keyword.

Muyinda Rogers
  • 147
  • 3
  • 13
  • 1
    OP said he wanted to skip writing constructors in the subclass; as they'd all be identical. – A. Bandtock Apr 06 '18 at 11:25
  • true, I just dont know how he would achieve that , because, every class needs to be instantiated by default. but I stand to be corrected. – Muyinda Rogers Apr 06 '18 at 11:28
  • @MuyindaRogers I appreciate your effort, but if you don't know how to achieve what is asked, maybe it is better not to answer? – lexicore Apr 06 '18 at 11:30
  • @lexicore I think thats a rude way , you chase away people from expressing and stand to be corrected. its not a matter of down voting and giving nothing in return. – Muyinda Rogers Apr 06 '18 at 11:47
  • I am the one that have down-voted..The reason is that you have not answered the question at all. You can't simply write a method that will replace a constructor (especially if you don't call it), `super(this)` doesn't make sense here (and will not compile). And of course, there is no explanation, which doesn't help. – AxelH Apr 06 '18 at 11:49
  • @MuyindaRogers I am sorry that it came out rude. It was not my intention. And I actually do not see my comment as rude. But please feel free to flag it as being rude/not constructive, moderators will deal with it. I also did not downvote your answer. And I really appreciate your effort. – lexicore Apr 06 '18 at 11:50
-1

Some thoughts (1) you should make entity "protected" instead of "private" - that's how you make it available in the subclass, (2) it helps to use accessor methods (getter/setter) which can be inherited by subclass unlike non-defaul constructors, (3) the operate method needs a return type (I used void below), (4) the operate method needs the same signature (type sensitive name and argument types) in order to override (5) it is good practice to annotate overridden methods with @Override.

public abstract class AbstractSuperClass {
  protected Entity entity;

  public AbstractSuperClass() {
  }

  public AbstractSuperClass(Entity entity) {
    this.entity = entity;
  }

  public setEntity(Entity entity) {
    this.entity = entity;
  }

  public abstract void operate();
}

public class SubClass extends AbstractSuperClass {
  @Override
  public void operate() {
    this.entity.doVoidMethod(); // protected entity is available in subclass
  }
}

// ... somewhere else
Entity instantiatedEntity = new Entity();
SubClass instance = new SubClass(); // default constructor
instance.setEntity(instantiatedEntity); // inherited method
instance.operate(); // yes calls entity.doVoidMethod()
pamcevoy
  • 1,136
  • 11
  • 15
  • It doesn't compile ... `SubClass` default constructor will not found `AbsthractSuperClass` constructor with no argument. And there is a lot of unecessary information. – AxelH Apr 06 '18 at 11:45
  • Good point. I added a default constructor in the parent class so the subclass will find it. The extra comments are just or clarity for the original poster. – pamcevoy Apr 06 '18 at 14:16
  • Downvoted because this kind of setter would make the code more error-prone and less maintainable. – Spotted Apr 06 '18 at 14:41