When Do I Use Super()

When do I use super()?

Calling exactly super() is always redundant. It's explicitly doing what would be implicitly done otherwise. That's because if you omit a call to the super constructor, the no-argument super constructor will be invoked automatically anyway. Not to say that it's bad style; some people like being explicit.

However, where it becomes useful is when the super constructor takes arguments that you want to pass in from the subclass.

public class Animal {
private final String noise;
protected Animal(String noise) {
this.noise = noise;
}

public void makeNoise() {
System.out.println(noise);
}
}

public class Pig extends Animal {
public Pig() {
super("Oink");
}
}

Do i need super when creating a subclass or not?

JLS 8.8.7. Constructor Body

If a constructor body does not begin with an explicit constructor invocation and the constructor being declared is not part of the primordial class Object, then the constructor body implicitly begins with a superclass constructor invocation "super();", an invocation of the constructor of its direct superclass that takes no arguments.

In

class Base {

Base() {

}
}

public class test2 extends Base {

test2() {

//super();
System.out.print("test2");
}
}

The commented out line is added automatically and since the superclass's no-argument constructor is defined, there is no error.

In the case of

class Quest {

Quest(int y) {

System.out.print("A:"+y);
}
}

class Quest1 extends Quest {

Quest1(int x) {

//super(x+1);
System.out.print("B:"+x);
}
}

The implicit call super() is trying to invoke an undefined constructor in the superclass, which causes the error

Implicit super constructor Quest() is undefined. Must explicitly invoke another constructor.

Uncommenting your explicit constructor call replaces the implicit call and thus the problem is resolved. Alternatively, define a no-argument constructor in the superclass.

Understanding Python super() with __init__() methods

super() lets you avoid referring to the base class explicitly, which can be nice. But the main advantage comes with multiple inheritance, where all sorts of fun stuff can happen. See the standard docs on super if you haven't already.

Note that the syntax changed in Python 3.0: you can just say super().__init__() instead of super(ChildB, self).__init__() which IMO is quite a bit nicer. The standard docs also refer to a guide to using super() which is quite explanatory.

Is it a good idea to use super() in Python?

The book Expert Python Programming has discussed the topic of "super pitfalls" in chapter 3. It is worth reading. Below is the book's conclusion:

Super usage has to be consistent: In a class hierarchy, super should be used everywhere or nowhere. Mixing super and classic calls is a confusing practice. People tend to avoid super, for their code to be more explicit.

Edit: Today I read this part of the book again. I'll copy some more sentences, since super usage is tricky:

  • Avoid multiple inheritance in your code.
  • Be consistent with its usage and don't mix new-style and
    old-style.
  • Check the class hierarchy before calling its methods in
    your subclass.

super() in Java

super() calls the parent constructor with no arguments.

It can be used also with arguments. I.e. super(argument1) and it will call the constructor that accepts 1 parameter of the type of argument1 (if exists).

Also it can be used to call methods from the parent. I.e. super.aMethod()

More info and tutorial here

What does 'super' do in Python? - difference between super().__init__() and explicit superclass __init__()

The benefits of super() in single-inheritance are minimal -- mostly, you don't have to hard-code the name of the base class into every method that uses its parent methods.

However, it's almost impossible to use multiple-inheritance without super(). This includes common idioms like mixins, interfaces, abstract classes, etc. This extends to code that later extends yours. If somebody later wanted to write a class that extended Child and a mixin, their code would not work properly.

What does calling super() in a React constructor do?

super() is called inside a react component only if it has a constructor. For example, the below code doesn't require super:

class App extends React.component {
render(){
return <div>Hello { this.props.world }</div>;
}
}

However if we have a constructor then super() is mandatory:

class App extends React.component {
constructor(){
console.log(this) //Error: 'this' is not allowed before super()

}
}

The reason why this cannot be allowed before super() is because this is uninitialized if super() is not called. However even if we are not using this we need a super() inside a constructor because ES6 class constructors MUST call super if they are subclasses. Thus, you have to call super() as long as you have a constructor. (But a subclass does not have to have a constructor.)

We call super(props) inside the constructor if we have to use this.props, for example:

class App extends React.component{
constructor(props){
super(props);
console.log(this.props); // prints out whatever is inside props

}
}

I hope I could make it clear.

Why is super.super.method(); not allowed in Java?

It violates encapsulation. You shouldn't be able to bypass the parent class's behaviour. It makes sense to sometimes be able to bypass your own class's behaviour (particularly from within the same method) but not your parent's. For example, suppose we have a base "collection of items", a subclass representing "a collection of red items" and a subclass of that representing "a collection of big red items". It makes sense to have:

public class Items
{
public void add(Item item) { ... }
}

public class RedItems extends Items
{
@Override
public void add(Item item)
{
if (!item.isRed())
{
throw new NotRedItemException();
}
super.add(item);
}
}

public class BigRedItems extends RedItems
{
@Override
public void add(Item item)
{
if (!item.isBig())
{
throw new NotBigItemException();
}
super.add(item);
}
}

That's fine - RedItems can always be confident that the items it contains are all red. Now suppose we were able to call super.super.add():

public class NaughtyItems extends RedItems
{
@Override
public void add(Item item)
{
// I don't care if it's red or not. Take that, RedItems!
super.super.add(item);
}
}

Now we could add whatever we like, and the invariant in RedItems is broken.

Does that make sense?



Related Topics



Leave a reply



Submit