Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What really happens on inheritance in Java?

Tags:

Suppose I have two classes Parent and Child, and Child inherits from Parent. I have three methods in Parent, out of which two are public and one is private.

Normally we say that all the non-private methods are inherited into the Child class, but I'm confused about exactly what happens. Does Java make a copy of the methods in the Child class, or does it use some kind of reference to maintain the relationship?

class Parent{     // Private method     private void method1(){         System.out.println("In private method of Parent class");     }     void method2(){     // calling private method         method1();     }     void method3(){     // calling private method         method1();     } }  class Child extends Parent{  }  class MainClass{    public static void main(String[] args){        Child child = new Child();        // calling non-private method which internally calls the private method        child.method2();    } } 
like image 260
Harshit Gupta Avatar asked Sep 08 '15 10:09

Harshit Gupta


People also ask

What happens in inheritance in Java?

Inheritance is one of the key features of OOP that allows us to create a new class from an existing class. The new class that is created is known as subclass (child or derived class) and the existing class from where the child class is derived is known as superclass (parent or base class).

What is the real life example of inheritance in Java?

Inheritance is the capability of one class to inherit capabilities or properties from another class in Java. For instance, we are humans. We inherit certain properties from the class 'Human' such as the ability to speak, breathe, eat, drink, etc. We can also take the example of cars.

What happens when a class is inherited?

Inheritance enables you to create new classes that reuse, extend, and modify the behavior defined in other classes. The class whose members are inherited is called the base class, and the class that inherits those members is called the derived class.

How does inheritance mechanism take place during the execution of a program?

Inheritance allows programmers to create classes that are built upon existing classes, to specify a new implementation while maintaining the same behaviors (realizing an interface), to reuse code and to independently extend original software via public classes and interfaces.

What is the purpose of inheritance in Java?

The idea behind inheritance in Java is that you can create new classes that are built upon existing classes. When you inherit from an existing class, you can reuse methods and fields of the parent class.

What is an inherited class in Java?

It is also called a base class or a parent class. Reusability: As the name specifies, reusability is a mechanism which facilitates you to reuse the fields and methods of the existing class when you create a new class. You can use the same fields and methods already defined in the previous class. The syntax of Java Inheritance

What is multiple inheritance in Java?

Note: Multiple inheritance is not supported in Java through class. When one class inherits multiple classes, it is known as multiple inheritance. For Example: When a class inherits another class, it is known as a single inheritance.

How to achieve hybrid inheritance in Java?

In java, we can achieve hybrid inheritance only through Interfaces. Default superclass: Except Object class, which has no superclass, every class has one and only one direct superclass (single inheritance).


2 Answers

Does Java makes copy of the methods in the Child class or it uses some kind of reference to maintain the relationship?

Latter. Take a look at invokespecial. Java recursively looks up methods one class at a time. The first matching method is called. This is why calling a virtual (default) method is slower than calling a final method.

In general, the actual code within a method is not copied when you inherit from a class containing that method.

like image 166
Navin Avatar answered Nov 14 '22 09:11

Navin


Neither.

Inheritance is a programming language concept, not a real action. When you investigate the compiled Child class, e.g. with javap, you won’t find any artifact related to the three methods of Parent. There will be the information that Child has the superclass Parent, but no mentioning of the inherited methods, neither as references nor as copies.

The fact that Child conceptionally inherits methods from Parent comes into play when you actually try to invoke one of them through a variable whose compile-time type is Child, like in your Test class. Then it is up to the compiler to find the inherited methods in order to compile the code containing the invocation correctly. It is also up to the compiler whether it searches the class hierarchy every time it resolves a target method of an invocation or whether it collects the existing methods in certain data structures to speed up subsequent lookups and which data structures it uses.

This process is more complicated than you might think. There may be multiple candidates among which the compiler has to select one and it may even fail due to ambiguity. The result of the process will be a decision about whether the invocation is valid and, in case it is valid, a single target method and its actual signature.

The compiled invocation will contain the name and signature of the target method and a reference to the compile time type of the reference on which it is invoked, i.e. Child. It will not contain the information that the actual method has been inherited from Parent. This is intentional. Whether Child declares the method itself, inherits it from Parent or overrides a method of Parent should not affect the code of the invoker Test nor the compatibility between compiled class files.


This implies that at runtime a class like Test may contain a reference, given by name and signature, to a method in Child not being stored in the class file of Child, in other words, the JVM is responsible as well, for making the concept of inheritance working. At the same time, it has to ensure that the concept of overriding works, when a method invocation is executed.

The way it implements this is also unspecified, leaving room for different strategies. Searching class hierarchies on every invocation would be legal, but lead to poor performance.

A common technique is a vtable. Associated with every class is a table (array) containing references to the available methods, be it declared or inherited. On initialization of a subclass, its table will start with a copy of the superclass’ table, having entries for new methods appended at the end and entries of overridden methods changed. At some time, the method invocation will be linked by finding the index of the vtable entry, appropriate to the specified name and signature. A typical strategy is to do the lookup on the first invocation. The instruction is then modified to refer to the index to avoid subsequent lookups. From then, subsequent executions consist of fetching the vtable for an object’s runtime class and getting the method reference from the table’s entry.

Considering that, you could say that at runtime, inheritance is typically implemented as some kind of reference—but wait.

Implementations like Oracle’s JVM are capable of doing hotspot optimizations in which the context of often executed code is considered. There might be, for example an inherited method which itself invokes methods which have been overridden in some subclasses. When the JVM finds out that this method is called very often on a single concrete subclass, it may create an optimized version for that particular case. Then, a copy of the method’s code will be the starting point for the subsequent code transformations, inlining code of the specific subclass, etc.

Since such sophisticated implementations will use references for non-optimized code while using optimized copies in other cases, an alternative to the initial answer answer could be:

Both.

like image 38
Holger Avatar answered Nov 14 '22 11:11

Holger