What's the different between super and super() in java? - java

like this:
public class class1 {
public void xxx(){
super.getXXX();
super().getXXX();
}
}

Both are used in a subclass as a way to invoke or refer to its superclass.
super() is a method call you make inside a constructor or inside an overridden method to invoke the superclass's constructor or the superclass's overridden method. The super() call can also take arguments in these cases.
Note that since all classes by default at least inherit from Object, you can always call super() inside a constructor (it must be the first statement in the constructor though). This super() call is in fact ordinarily inserted by the compiler into your no-arg constructor by default.
This can get tricky however if the superclass doesn't have a no-arg constructor though, in which case your call to super() will fail without the appropriate args. A no-arg constructor is ordinarily generated by default however so you don't have to worry about it, but it won't be automatically generated if you've explicitly define another constructor with args, so that's when you may need to explicitly define one yourself.
super without the parens on the other hand is simply a reference to the superclass itself, like any other variable. It can be used to invoke any accessible method in that class or to refer to any of the class's accessible fields, just like you would with any other reference. Eg: super.doSomething() or super.x

Every class in java has a Superclass. When you use the super keyword, you are referring to super class, and the dot operator on super will give you access to the Super class's properties and methods.
super() is the constructor of super class. When you override the constructor in a subclass, you have to call super() before you can execute your own logic, and if you don't, the compiler, on your behalf, will insert a call to the no-args constructor. (Sometimes, there isn't one, and the code fails in compilation)
While in Java, calling the constructor gives you an instance of the class, it isn't the same thing when you do a super(), because there isn't a separate instance of the super class getting created when you do a super(). Hence, while MyClass().doSomething() is a perfectly valid call, super().doSomethingElse() is not.

Related

Program initialises both subclas and superclass constructors at once [duplicate]

Consider this code:
class Test {
Test() {
System.out.println("In constructor of Superclass");
}
int adds(int n1, int n2) {
return(n1+n2);
}
void print(int sum) {
System.out.println("the sums are " + sum);
}
}
class Test1 extends Test {
Test1(int n1, int n2) {
System.out.println("In constructor of Subclass");
int sum = this.adds(n1,n2);
this.print(sum);
}
public static void main(String[] args) {
Test1 a=new Test1(13,12);
Test c=new Test1(15,14);
}
}
If we have a constructor in super class, it will be invoked by every object that we construct for the child class (ex. Object a for class Test1 calls Test1(int n1, int n2) and as well as its parent Test()).
Why does this happen?
The output of this program is:
In constructor of Superclass
In constructor of Subclass
the sums are 25
In constructor of Superclass
In constructor of Subclass
the sums are 29
Because it will ensure that when a constructor is invoked, it can rely on all the fields in its superclass being initialised.
see 3.4.4 in here
Yes. A superclass must be constructed before a derived class could be constructed too, otherwise some fields that should be available in the derived class could be not initialized.
A little note:
If you have to explicitly call the super class constructor and pass it some parameters:
baseClassConstructor(){
super(someParams);
}
then the super constructor must be the first method call into derived constructor.
For example this won't compile:
baseClassConstructor(){
foo();
super(someParams); // compilation error
}
super() is added in each class constructor automatically by compiler.
As we know well that default constructor is provided by compiler automatically but it also adds super() for the first statement.If you are creating your own constructor and you don't have either this() or super() as the first statement, compiler will provide super() as the first statement of the constructor.
Java classes are instantiated in the following order:
(at classload time)
0. initializers for static members and static initializer blocks, in order
of declaration.
(at each new object)
create local variables for constructor arguments
if constructor begins with invocation of another constructor for the
class, evaluate the arguments and recurse to previous step. All steps
are completed for that constructor, including further recursion of
constructor calls, before continuing.
if the superclass hasn't been constructed by the above, construct the
the superclass (using the no-arg constructor if not specified). Like #2,
go through all of these steps for the superclass, including constructing
IT'S superclass, before continuing.
initializers for instance variables and non-static initializer blocks, in
order of declaration.
rest of the constructor.
That´s how Java works. If you create a child object, the super constructor is (implicitly) called.
In simple words if super class has parameterized constructor, you need to explicitly call super(params) in the first line of your child class constructor else implicitly all super class constructors are called untill object class is reachead.
The subclass inherits fields from it's superclass(es) and those fields have to get constructed/initialised (that's the usual purpose of a constructor: init the class members so that the instance works as required. We know that some people but a lot more functionality in those poor constructors...)
Constructor implements logic that makes the object ready to work. Object may hold state in private fields, so only its class' methods can access them. So if you wish instance of your subclass be really ready to work after calling constructor (i.e. all its functionality including inherited from base class is OK) the base class's constructor must be called.
This is why the system works this way.
Automatically the default constructor of base class is called. If you want to change this you have to explicitly call constructor of base class by writing super() in the first line of your subclass' constructor.
The base class constructor will be called before the derived class constructor. This makes sense because it guarantees that the base class is properly constructed when the constructor for the derived class is executed. This allows you to use some of the data from the base class during construction of the derived class.
When we create an object of subclass, it must take into consideration all the member functions and member variables defined in the superclass. A case might arise in which some member variable might be initialized in some of the superclass constructors. Hence when we create a subclass object, all the constructors in the corresponding inheritance tree are called in the top-bottom fashion.
Specifically when a variable is defined as protected it will always be accessible in the subclass irrespective of whether the subclass is in the same package or not. Now from the subclass if we call a superclass function to print the value of this protected variable(which may be initialized in the constructor of the superclass) we must get the correct initialized value.Hence all the superclass constructors are invoked.
Internally Java calls super() in each constructor. So each subclass constructor calls it's superclass constructor using super() and hence they are executed in top-bottom fashion.
Note : Functions can be overridden not the variables.
Since you are inheriting base class properties into derived class, there may be some situations where your derived class constructor requires some of the base class variables to initialize its variables. So first it has to initialize base class variables, and then derived class variables. That's why Java calls first base class constructor, and then derived class constructor.
And also it doesn't make any sens to initialize child class with out initializing parent class.
Constructor of Super class in called first because all the methods in the program firstly present in heap and after compilation they stores in to the stack,due to which super class constructor is called first.
There is a default super() call in your default constructors of sub classes.
//Default constructor of subClass
subClass() {
super();
}
"If a constructor does not explicitly invoke a superclass constructor, the Java compiler automatically inserts a call to the no-argument constructor of the superclass. If the super class does not have a no-argument constructor, you will get a compile-time error. Object does have such a constructor, so if Object is the only superclass, there is no problem."
(source: https://docs.oracle.com/javase/tutorial/java/IandI/super.html)
I'll try to answer this from a different perspective.
Suppose Java didn't call the super constructor for you automatically. If you inherit the class, you'd have to either call the super constructor implicitly, or rewrite it yourself. This would require you to have internal knowledge of how the super class works, which is bad. It would also require to to rewrite code, which is also not good.
I agree that calling the super constructor behind the scenes is a little unintuitive. On the other hand, I'm not sure how they could have done this in a more intuitive way.
As we know that member variables(fields)of a class must be initialized before creating an object because these fields represent the state of object. If these fields are explicitely not initilized then compiler implicitely provides them default values by calling no-argument default constructor. Thats why subclass constructor invokes super class no-argument default constructor or implicitely invoked by compiler .Local variables are not provided default values by compiler.
here your extending Test to your test1 class meaning u can access all the methods and variable of test in your test1. keep in note that u can access a class methods or variable only if memory is allocated to it and for that it need some constructor either a default or parameterized ,so here wen the compiler finds that it is extending a class it will try to find the super class constructor so that u can access all its methods.
Parents Exits First!!
And like real world Child Can't exist without the Parents..
So initialising parents(SuperClass) first is important in order to use thrm in the children(Subclass) Classes..

How does default constructor used to instantiate object if it's super class no argument constructor has empty body?

default constructor invoke no_argument constructor in super class reference
and this last constructor used to instantiate object from this class,How ? i mean what does superclass constructor body exactly do ?
example
public class Child extend Fragment {}
if i tried to instantiate this class Child
Child a = new Child() ;
while compiling compiler invoke no-argument constructor in Fragment class .
in android.app package i found that no-argument constructor has no body
public Fragment() {}
Question how could this constructor be useful ? it do nothing !
P.S
i mean by
how could this constructor be useful?
how does it instantiate its class although it empty , where is the code that instantiate super class?
Question how could this constructor be useful ? it do nothing !
The purpose of a constructor, whether empty or not, is to provide an instance of the class. The constructor body, if it exists, may further do additional operations necessary when first creating the instance.
The constructor may not be doing anything itself but it returns an instance, on which you may further call public methods defined in the class.
For example, in your mentioned Fragment class, let's suppose there is an attach() method. If the attach() method is non-static, you will need to create an instance (using the empty constructor) to call the attach() method on it irrespective of whether the constructor does anything or not.
how does it instantiate its class although it empty
A constructor doesn't need any code in its body to be instantiated.
Calling new ClassName() (with appropriate parameters, if any) is enough. It is the job of JVM to create the object at runtime. You don't need to write any specific code inside a constructor for that. That extra code, if you wish, can help the instance start off with a specific state by setting some fields or calling methods, etc.
where is the code that instantiate super class?
A constructor in a subclass (or any class, for that matter) only generates an instance of that class. It doesn't need to instantiate its super class. You may call the super class constructor (using super()) if it has some important initialization code, but it's not compulsory. Also, subclasses don't inherit constructors from super classes. But they do inherit the public and protected fields and methods.
Regarding the Fragment class, you have have some confusion regarding its use which can be clarified here.
The syntax for calling a superclass constructor is
super();
or:
super(parameter list);
Question how could this constructor be useful ? it do nothing !
The super constructor could be used to initialized properties common for all subclasses. If it's empty it still can be used by reflection API.
Fragment.class.getConstructor().newInstance();
or
Child a = new Child() ;
a.getClass().getSuperclass().getConstructor().newInstance();
the last line explicitly invokes a constructor of the superclass.
an empty constructor (aka default constructor) means only that an instance can be created without any further work. This can be due to framework requirements or the instantation is ok with the default values for the attributes.
If the empty constructor is the only constructor in the class, it is not required to write it, its there by default.
Although if there are other constructors (with parameters), one must explicitly state the default constructor.

A inherits from B, B inherits from C. Will initializing A invoke constructor of C?

As I was preparing for an interview about OOP, I came across this question.
A inherits form B. B inherits from C.
Will initializing A invoke constructor of C?
What I know is that a constructed is not inherited. We have to use the super keyword to refer to the parent's constructor. Am I right?
The constructor of a subclass will first invoke the constructor of its super class. If a class has several ancestors, these calls will be stacked until the constructor of the top ancestor is called. Then, it will continue executing the constructor of the next ancestors until all the constructor of the ancestors were executed. You can infer from here that every time you create an object, the constructor of Object class is invoked, always.
Note that if you don't add the call to super() in the subclass constructor, the compiler will add it for you automatically. If there's no default constructor for the super class and you don't specify the call to the specific constructor of the super class in the constructor of the subclass, then you will get a compiler error.
All these rules are stated in JLS.
In the world of Java, when you are extending another class, you only see your direct super class' constructor. The super class is supposed to proper encapsulate the super-super class constructor.
There will always be an implicit call to the constructor of the base class. In your case, the constructor of C will be called first, then the constructor of B and finally the constructor of A.
Using super is useful when you have defined overloaded constructors, and you want to call a specific one.

Calling super() on a class with no constructor

I just noticed in the codebase of a very large project I am assigned at work, a particular class has no constructor. Its subclass though, calls super().
Can someone please explain what is going when a subclass calls super(), but there is no constructor in the parent?
(I can guess that the effect is like calling an empty constructor, but I am wondering if there is anything else going on behind the scenes).
If you do not have any parameterized constructor and I strictly mean no constructor then and only then java will add a default constructor(One with no parameters) for you.
Each constructor must call a constructor of it's super class. You cannot perform any other action in the subclass constructor untill all constructors of superclasses up the inheritance tree are called. Hence this call must be the 1st line of your subclass constructor If you do not provide one again java does that for you.
Refer
Why does this() and super() have to be the first statement in a constructor?
If a class doesnt having any constructors means it is gifted with empty constructor by the java compiler.
If you place the empty constructor , then the compiler will not because it is already mentioned by you.
Now If you want your own constructor with your own parameters, Then there will not be any default constructor by the java compiler
Check this for more info on constructors
Subclass constructor always call its parent constructor first before executing any statement. If there is no consturctor in parent class then whether you call it or not explicitly, super() call will be added in the code by java compiler and hence will be executed by JVM.
The java compiler will provide a default no argument constructor without a body when a class doesn't declare any constructors. Calling super() in a base class constructor will invoke that default constructor.
Can someone please explain what is going when a subclass calls
super(), but there is no constructor in the parent?
If parent class doesn't have any constructor then java compiler will call the default constructor of it. If you don't want to call default constructor then you can create your own empty constructor in that class.
Compiler add a default constructor with no parameter into your class if you do not provide it explicitly. So in your case it is calling default constructor.

Super constructor call

In Java, if my class extends a super class and by default the first line of the constructor is Super(), are the fields of the super class initialized, or is just the constructor run?
Also, if the constructor in the superclass calls a method that happens to be in both classes, does it run the super class or sub class version?
In Java, if my class extends a super class and by default the first line of the constructor is Super(), are the fields of the super class initialised? or is just the constructor run?
The fields of the superclass are always initialized prior to the superclass constructor body running.
See section 15.9.4 and section 12.5 of the JLS for details.
Also, if the constructor in the superclass calls a method that happens to be in both classes, does it run the super class or sub class version?
Assuming the subclass method actually overrides the superclass one, the subclass implementation will be called. This is generally seen as a Bad Thing, as it means the method can't rely on anything initialized by the subclass constructor.
the fields of the super class initialized, or is just the constructor run?
It's the same thing. The following things happen when a constructor is called:
The superclass constructor is called, unless the current class is java.lang.Object.
The instance variable declarations with initializers and any anonymous initializers { } are executed.
The code in the constructor following the (implicit or explicit) super() call is executed.
You can see that by recursion when you call super(), step (2) precedes step (3). So yes, the instance variables are initialized and the constructor code is executed.
Also, if the constructor in the superclass calls a method that happens to be in both classes, does it run the super class or sub class version?
The subclass version. Note that this is different from C++ where the object is viewed as partially constructed, ditto the v-table, so the superclass version will be run.

Categories