Pages

Sunday, March 5, 2017

Method Overrriding

When a sub class declares a method which exists in super class, then it is called Method Overriding.

Example:
class SuperClass {

    void m1(){
        System.out.println("SuperClass -> m1()");
    }
    
    void m2(){
        System.out.println("SuperClass -> m2()");
    }
}


class SubClass extends SuperClass{
    
    void m2(){
        System.out.println("SubClass -> m2()");
    }
    
    void m3(){
        System.out.println("SubClass -> m3()");
    }
}


class Lab{
    public static void main(String[] args) {
        SubClass sb = new SubClass();
        sb.m1();
        sb.m2();
        sb.m3();
        
    }
}


Notes on the above program:

  • "SubClass" class has implemented m2() method of SuperClass with the same signature i.e m2() method is overriden in SubClass.
  • m1() method of SuperClass is not implemented in SubClass class but m1() method of SuperClass is inherited to SubClass.
  • m3() method is the newly added method in "SuperClass" class.

Why Override the method?

  • According to OOPS, "Classes are closed for modifications" i.e if you want to modify the functionality of existing class, then you should not disturb existing class.
  • It is always better to write a sub class and provide the required implementations in sub class.
  • Sub Class can be written for following purposes:
    • To add functionality
    • To modify existing functionality
    • To inherit existing functionality.

Rules to override the method.

  1. Subclass method name must be same as super class method name.
  2. Subclass method parameters (type, order and number) must be same as super class method parameters.
  3. Subclass method return type must be same as super class method return type.
    Note: If the super class method return type is class type then while overriding the method in subclass you can use same class type or its subclass as return type (FROM JAVA 5).
    Example:
    class A{}
    
    class B extends A{}
    
    class C{}
    
    
    class SuperClass{
        A m1(){...};
    }
    
    class SubClass extends SuperClass{
        A m1(){...};
        B m1(){...}; //Valid from Java 5
        C m1(){...}; //Invalid
    }
    

  4. Subclass method access modifier must be same or higher than super class method access modifier:
    Super Class
    Sub Class
    public
    public
    protected
    protected, public
    default
    default, protected, public
    private
    private, default, protected, public

  5. When super class method is instance method, then you have to override in sub class as instance only.
  6. When super class method is static method then you have override in sub class as static only.
  7. When super class method is throwing some method level checked exception then sub class method can/cannot do the the following:
    1. Sub class method can ignore method level exception
    2. Subclass method can throw the same exception
    3. Subclass method can throw the exception which is sub class to super class method exception.
    4. Subclass method cannot throw the exception which is super class to super class method exception.
    5. Subclass method cannot throw the exception which is non subclass to super class method exception. i.e cannot throw a new checked exception.
    6. Subclass method can throw any unchecked exception.
  8. When super class method is throwing some method level unchecked exception then sub class method can do the following:
    1. Sub class method can ignore that method level exception.
    2. Sub class method can throw the same exception.
    3. Sub class method can throw any other unchecked exception.
    4. Sub class method cannot throw any checked exception.



Example 1:

class A{
    void show(){
        System.out.println("A->show()");
    }
}


class B extends A{
    void SHOW(){
        System.out.println("B->SHOW()");
    }
}


public class Lab1 {
    public static void main(String[] args) {
         B bObj = new B();
         bObj.show();
         bObj.SHOW();   //NOT OVERRIDING, JAVA IS CASE SENSITIVE.
    }       
}

Example 2:

public class Lab2 {
    public static void main(String[] args) {
        B bObj = new B();
        bObj.show(99);
        bObj.show("Sujay");
    }
}

class A{
    void show(int ab){
        System.out.println("A->show(int)");
    }
}


class B extends A{
    void show(String ab){
        System.out.println("B->show(String)");
    }
}
//In this case, Overloading is at play and not Overriding

Example 3:

class Lab3{
    public void main(String args[]){
        B bObj = new B();
        bObj.show();on
    }
}

class A{
    long show(){
        return 0;
    }
}

class B extends A{
    int show(){
        return 0;
    }
}
/*CTE

Lab3.java:15: error: show() in B cannot override show() in A
        int show(){
            ^
  return type int is not compatible with long
1 error
*/

Example 4:


class Lab4{
    public static void main(String args[]){
        SubC sb = new SubC();
        sb.m1();
    }
}

class SuperC{
    A m1(){
        return new A();
    }
}

class SubC{
    B m1(){
        return new B();
    }
}

class A{}
class B{}

/*
C.T.E
No relation between A and B
*/

Example 5:


class Lab7{
    public void main(String args[]){
        B bObj = new B();
        bObj.m1();
    }
}

class A{
    final void m1(){
        return;
    }
}

class B extends A{
    void m1(){
        return;
    }
}
/*
final method cannot be overriden
final method will be inherited
final class cannotbe extended by sub class
*/

Example 6:

class Lab8{
    public void main(String args[]){
        B bObj = new B();
        bObj.m1();
    }
}

class A{
    void m1(){
        return;
    }
}

class B extends A{
    final void m1(){
        return;
    }
}
/*
m1() is overriden in B, but cannot be overriden any further.
*/

Example 7:

class Lab9{
    public void main(String args[]){
        B bObj = new B();
        bObj.m1();
    }
}

class A{
    void m1(){
        return;
    }
}

class B extends A{
    static void m1(){
        return;
    }
}

/*
m1() in A is non-static. Therefore, cannot be overriden as static


Lab9.java:15: error: m1() in B cannot override m1() in A
        static void m1(){
                    ^
  overriding method is static
1 error
*/

Example 8:

class Lab10{
    public void main(String args[]){
        B bObj = new B();
        bObj.m1();
    }
}

class A{
    static void m1(){
        return;
    }
}

class B extends A{
    void m1(){
        return;
    }
}

/*
m1() in A is static, it cannot be overriden as static

Lab10.java:15: error: m1() in B cannot override m1() in A
        void m1(){
             ^
  overridden method is static
1 error
*/

Example 9:

class Lab11{
    public void main(String args[]){
        B bObj = new B();
        bObj.m1();
    }
}

class A{
    static void m1(){
        return;
    }
}

class B extends A{
    static void m1(){
        return;
    }
}
/*compile fine*/

Example 10:

class Lab12{
    public void main(String args[]){
        B.m1(); //cannot call m1() by class name as static
    }
}

class A{
    void m1(){}
    static void m2(){}
}

class B extends A{
    void m1(){}
    static void m2(){}
}

/*
CTE

Lab12.java:3: error: non-static method m1() cannot be referenced from a static context
                B.m1(); //cannot call m1() by class name as static
                 ^
1 error
*/

Example 11:

class Lab13{
    public void main(String args[]){
        new B().m1(); 
    }
}

class A{
    private void m1(){} //private method is not visible in sub class.
}

class B extends A{
    //private void m1(){} throws compile time error
    void m1(){} //no compile time error now...works fine
}

Example 12:

Example 13:

Example 14:

Example 15:


Sunday, February 19, 2017

Access modifiers

Access modifiers can be used to specify the scope or visibility of the class or the members of the class.

There are four access modifiers:
a. public
b. protected
c. default
d. public

Private scope:
-------------
1. Private scope is also called class scope, i.e private members must be accessed from the same class where it is declared.
2. Private members cannot be accessed from outside the class, not even from sub class i.e private members will not be inherited to sub classes.
3. Private modifier can be used only for members of the class not for class itself.


Default scope:
--------------
1. When you are not using any using any modifier with the members of the class then the scope of the members will be default scope.
2. Default scope is also called package scope i.e default members can be accessed from the same class, sub class and non sub class which are in the same package.
3. Default members cannot be accessed from outside the package i.e default members will not be inherited to sub class available in outside the package.
4. Default scope is available for both class and its members.


Protected scope:
----------------
1. Protected members can be accessed from the same class, sub class and non sub class which are available in the same package.
2. Protected members can be accessed from the sub classes which are available in different package.
3. Protected members cannot be accessed from the non sub classes which are available in different package.
4. Protected modifier can be used only for members of the class not for class itself.


Public scope:
-------------
1. Public members can be accessed from anywhere.
2. Public modifier can be used for both class and their members.



Example 1: The following programs demonstrate how member variables of class - A can be accessed from classes in the same package and different package.

package com.pack.p1;

public class A{
    
    private int a=10;
    int b =20;
    protected int c=30;
    public int d=40;
    
    public void showA(){
        System.out.println("A->showA()");
        System.out.println("#Direct#");
        System.out.println(a);
        System.out.println(b);
        System.out.println(c);
        System.out.println(d);
        System.out.println("#A-Object#");
        A a1 = new A();
        System.out.println(a1.a);
        System.out.println(a1.b);
        System.out.println(a1.c);
        System.out.println(a1.d);
        
    }
}



Accessing inherited member variables of class - A from a different class in the same package

package com.pack.p1;

public class B extends A{
        
    public void showB(){
        System.out.println("B->showB()");
        System.out.println("#Direct#");
        //System.out.println(a); private member of super class is not inherited
        System.out.println(b); //default is inherited
        System.out.println(c); //protected is inherited (package scope)
        System.out.println(d); //public is inherited
        
        System.out.println("#A-Object#");
        A a1 = new A();
        //System.out.println(a1.a); private member of a class cannot be accessed outside the class.
        System.out.println(a1.b); //default is inherited and can be accessed
        System.out.println(a1.c); //protected is inherited and can be accessed
        System.out.println(a1.d); //public is inherited and can be accessed
        
        System.out.println("#B-Object#");
        B b1 = new B();
        //System.out.println(b1.a); private member of super class is not inherited
        System.out.println(b1.b); //default is inherited and can be accessed
        System.out.println(b1.c); //protected is inherited and can be accessed
        System.out.println(b1.d); //public is inherited and can be accessed
        
    }
}

Accessing object of A from a class in the same package

package com.pack.p1;

public class C{
    
    public void showC(){
        System.out.println("C->showC()");
        System.out.println("#A-Object#");
        A a1 = new A();
        //System.out.println(a1.a); private member cannot be accessed outside the class.
        System.out.println(a1.b);
        System.out.println(a1.c);
        System.out.println(a1.d);
            
        
    }
}

Subclass of class - A from a different package
package com.pack.p2;
import com.pack.p1.A;

public class D extends A{
    
    public void showD(){
    
        System.out.println("D->showD()");
        System.out.println("#Direct#");
        //System.out.println(a);  private member will not be inherited
        //System.out.println(b); default member will not be inherited.
        System.out.println(c);
        System.out.println(d);
        
        System.out.println("#D-Object#");
        D d1 = new D();
        //System.out.println(d1.a); private member cannot be accessed outside the class.
        //System.out.println(d1.b); default member cannot be accessed outside the package.
        System.out.println(d1.c);
        System.out.println(d1.d);
        
        System.out.println("#super keyword#");
        //System.out.println(super.a); private member will not be inherited
        //System.out.println(super.b); default member cannot be accessed outside the package.
        System.out.println(super.c);
        System.out.println(super.d);
        
        A a1 = new A();
        System.out.println("#A-Object#");
        //System.out.println(a1.a); private member cannot be accessed outside the class.
        //System.out.println(a1.b); default member cannot be accessed outside the package.
        //System.out.println(a1.c); protected member cannot be accessed outside the package using the super class object.
        System.out.println(a1.d);
            
        
    }
}

Accessing object of class - A from a different package.

package com.pack.p2;
import com.pack.p1.A;

public class E{
    public void showE(){
        System.out.println("E->showE()");
        
        A a1 = new A();
        //System.out.println(a1.a); private member cannot be accessed outside the class.
        //System.out.println(a1.b); default member cannot be accessed outside the package.
        //System.out.println(a1.c); protected member cannot be accessed outside the package if it's not inherited.
        System.out.println(a1.d); //public can be accessed from anywhere.
    }
}

Test class to execute all the above classes

package com.pack.p3;
import com.pack.p1.*;
import com.pack.p2.*;

public class Lab2{
    public static void main(String args[]){
        
        A a1 = new A();
        a1.showA();
        
        B b1 = new B();
        b1.showB();
        
        C c1 = new C();
        c1.showC();
        
        D d1 = new D();
        d1.showD();
        
        E e1 = new E();
        e1.showE();
    }
}

/*

C:\JavaPractice\JLC Notes and Examples\Access Modifiers\src>java -cp ..\classes com.pack.p3.Lab2
A->showA()
#Direct#
10
20
30
40
#A-Object#
10
20
30
40
B->showB()
#Direct#
20
30
40
#A-Object#
20
30
40
#B-Object#
20
30
40
C->showC()
#A-Object#
20
30
40
D->showD()
#Direct#
30
40
#D-Object#
30
40
#super keyword#
30
40
#A-Object#
40
E->showE()
40

*/

Sunday, February 5, 2017

super keyword in Java


  • super is a keyword which is used to refer the members of immediate super class.
  • super cannot be accessed from static context.
  • super keyword can be used in 3 ways:
    1. To access the immediate super class variables
      Syntax:
                  super.<variableName>
    2. To access the immediate super class methods
      Syntax:
                  super.();
    3. To access the immediate super class constructors
      Syntax:
                  super(params);

Example 1

class Lab2
{
    public static void main(String[] args) 
    {
        Hello h = new Hello();
        h.show();
    }
}

class Hai
{
    int a = 10;
}

class Hello extends Hai
{
    int a = 20;

    void show(){
        int a = 30;
        System.out.println(a); 
        System.out.println(this.a);
        System.out.println(super.a);
    }
}

Example 2

class Lab4
{
    public static void main(String[] args) 
    {
        Hello h = new Hello();
        h.show();
    }
}

class Hai{
    static int a=10;
}

class Hello extends Hai
{
    static int a = 20;

    void show(){
        int a = 30;
        System.out.println(a); 
        System.out.println(this.a); //Hello.a by the compiler
        System.out.println(super.a);//Hai.a by the compiler
    }
}

/*
Because it is static, compiler replaces by the class name

output
30
20
10
*/

Example 3

this and super keywords cannot be accessed from static context
class Lab7
{
    public static void main(String[] args) 
    {
        Hello hello = new Hello();
        System.out.println(hello.a);
    }
}

class Hai
{
    int a;
}

class Hello extends Hai
{
    String a;
}

/*
output
null
*/

Example 4

class Lab8{
    public static void main(String args[]){
            new C().show();
    }
}

class A
{
    int a = 10;
}

class B extends A
{
    String a = "SRJ";
}

class C extends B
{
    boolean a = true;
    void show(){
        float a = 99.99F;
        System.out.println(a);
        System.out.println(this.a);
        System.out.println(super.a);
        System.out.println(super.super.a);
    }
}

/*
Compile Time Error

Lab8.java:22: error: <identifier> expected
                System.out.println(super.super.a);
                                         ^
Lab8.java:22: error: not a statement
                System.out.println(super.super.a);
                                              ^
Lab8.java:22: error: ';' expected
                System.out.println(super.super.a);
                                                ^
3 errors
*/

Example 5

class Lab9{
    public static void main(String args[]){
            new C().show();
    }
}

class A
{
    int a = 10;
    int getAData(){
        return this.a;
    }
}

class B extends A
{
    String a = "SRJ";
}

class C extends B
{
    boolean a = true;
    void show(){
        float a = 99.99F;
        System.out.println(a);
        System.out.println(this.a);
        System.out.println(super.a);
        System.out.println(getAData());
    }
}

/*
output:
99.99
true
SRJ
10
*/

Example 6

super keyword can be used to ONLY to reference parent class variable, method or invoke parent constructor
class Lab10 
{
    public static void main(String[] args) 
    {
        new Hello.show();
    }
}

class Hai{}

class Hello extends Hai
{
    void show(){
        System.out.println(this);
        System.out.println(super);
    }
}

/*
Lab10.java:15: error: '.' expected
                System.out.println(super);
                                        ^
Lab10.java:15: error: ')' expected
                System.out.println(super);
                                         ^
Lab10.java:15: error: ';' expected
                System.out.println(super);
                                          ^
Lab10.java:17: error: reached end of file while parsing
}
 ^
4 errors
*/

Example 7

super cannot be assigned to any reference variable. It can be used only along with parent class variable,method and constructors
class Lab11
{
    public static void main(String[] args) 
    {
        new Hello.show();
    }
}

class Hai{}

class Hello extends Hai
{
    void show(){
        Hai h1 = this;
        Hello h2 = super;
    }
}

/*
Lab11.java:15: error: '.' expected
                Hello h2 = super;
                                ^
Lab11.java:15: error: ';' expected
                Hello h2 = super;
                                 ^
Lab11.java:17: error: reached end of file while parsing
}
 ^
3 errors
*/

Example 8

Default constructor is not created in the parent class. The super() inserted by the compiler in the sub-class constructor tries calling parent class constructor
class Lab15{
    public static void main(String args[]){
        new B();
    }
}

class A{
    A(int a){
        System.out.println("A->(int) cons");
    }
}

class B extends A{
    B(){
        super();
        System.out.println("B->D.C");
    }
}

/*
Lab15.java:15: error: constructor A in class A cannot be applied to given types;
                super();
                ^
  required: int
  found: no arguments
  reason: actual and formal argument lists differ in length
1 error
*/

Example 9

super() has to be the first statement inside a constructor. If programmer doesn't provide super() or this() inside constructor
then compiler will automatically add super() in the first line of a constructor
class Lab18{
    public static void main(String args[]){
        new B();
    }
}

class A{
    A(int a){
        System.out.println("A->(int) cons");
    }
}

class B extends A{
    B(){
        System.out.println("B->D.C");
        super(10);
    }
}

/*
Lab18.java:14: error: constructor A in class A cannot be applied to given types;
        B(){
           ^
  required: int
  found: no arguments
  reason: actual and formal argument lists differ in length
Lab18.java:16: error: call to super must be first statement in constructor
                super(10);
                     ^
2 errors
*/

Example 10

class Lab23{
    public static void main(String  args[]){
        new B();
    }
}

class A{
    A(Object obj){
        System.out.println("A(Object) Cons");
    }
}

class B{
    B(){
        super(this);
        System.out.println("B() D.C");
    }
}

/*
Lab23.java:15: error: cannot reference this before supertype constructor has been called
                super(this);
                      ^
Lab23.java:15: error: constructor Object in class Object cannot be applied to given types;
                super(this);
                ^
  required: no arguments
  found: B
  reason: actual and formal argument lists differ in length
2 errors
*/

Example 11

class Lab22{
    public static void main(String  args[]){
        B obj = new B("SRJ", 10);
        obj.show();
    }
}

class A
{
    int a;

    A(int a){
        this.a = a;
        System.out.println("A(int)");
    }
}

class B extends A
{
    String a;

    B(String a1, int a2){
        super(a2);
        this.a = a1;
        System.out.println("B(String, int)");
    }

    void show(){
        System.out.println(this.a);
        System.out.println(super.a);
    }
}

/*
output:
A(int)
B(String, int)
SRJ
10
*/

Inheritance


  • Inheritance is the process of writing new class by inheriting commonly used state and behavior of existing class.
  • Existing class is called as Super class or Base class or Parent class.
  • Newly defined class is called as Sub class or Derived class or Child class.
  • The main purpose of Inheritance is code re usability i.e Inheritance can be used to re-use the properties and operations of the existing class in the newly defined class.

Types of Inheritance:

1. Simple Inheritance: 
 In this type, there is one super class and one sub class.
 Ex: 
       class A{...}
       class B extends A{...}

2. Multi Level Inheritance.
In this type:
  • One super class can have only one direct sub class and many indirect sub classes.
  • One sub class can have only one direct super class and many indirect super classes.
  Ex:
       class A{...}
       class B extends A{...}
       class C extends B{...}

3. Hierarchical Inheritance:
 In this type:
  • One super class can have many direct sub classes.
  • One sub class can have only one direct super class.
  Ex:
      class A{...}
      class B extends A{...}
      class C extends A{...}

4. Multiple Inheritance:
In this type:

  • One sub class can have many direct super classes.
  • One super class can have only one direct sub class.
Java doesn't support Multiple Inheritance with classes.
Java supports Multiple Inheritance only with interfaces.

Example 1

class Lab3 
{
    public static void main(String[] args) 
    {
        Hello hello = new Hello();
        System.out.println(hello.a);
        System.out.println(hello.b);

        Hai hai = new Hai();
        System.out.println(hai.a);
    }
}

class Hai
{
    int a = 10;
}

class Hello extends Hai
{
    int b = 20;
}

/*
10
20
10
*/

Example 2


class Lab5 
{
    public static void main(String[] args) 
    {
        Hai hai = new Hai();
        hai.m1();
        hai.m2();
    }
}

class Hello
{
    int a = 10;
    void m1(){
        System.out.println("Hello : m1 -> :"+a);
    }
}


class Hai extends Hello
{
    int b = 20;
    void m2(){
        System.out.println("Hai : m2 -> :"+b);
    }
}

/*
output:
Hello : m1 -> :10
Hai : m2 -> :20
*/

Example 3 : Multi Level Inheritance

class Lab6 
{
    public static void main(String[] args) 
    {
        C obj = new C();
        obj.m1();
        obj.m2();
        obj.m3();
    }
}

class A
{
    void m1(){
        System.out.println("A -> m1()");
    }
}

class B extends A
{
    void m2(){
        System.out.println("B -> m2()");
    }

}

class C extends B
{
    void m3(){
        System.out.println("C -> m3()");
    }

}

/*
output:
A -> m1()
B -> m2()
C -> m3()
*/

Example 4 : Hierarchical Inheritance

class Lab7{
    public static void main(String args[]){

        B bObj = new B();
        bObj.m1();
        bObj.m2();

        C cObj = new C();
        cObj.m1();
        cObj.m3();
    }
}

class A
{
    void m1(){
        System.out.println("A -> m1()");
    }
}

class B extends A
{
    void m2(){
        System.out.println("B -> m2()");
    }

}

class C extends A
{
    void m3(){
        System.out.println("C -> m3()");
    }

}

/*

A -> m1()
B -> m2()
A -> m1()
C -> m3()

*/

Example 5: Multiple Inheritance is not supported in Java with classes

class Lab8
{
    public static void main(String[] args) 
    {
        System.out.println("Hello World!");
    }
}

class A{}
class B{}
class C extends A, B{}

/*
Lab8.java:11: error: '{' expected
class C extends A, B{}
                 ^
1 error
*/

Example 6:Every class extends java.lang.Object class by default.

class Lab10 
{
    public static void main(String[] args) 
    {
        Hello h1 = new Hello();
        System.out.println(h1.toString());


        Hai h2 = new Hai();
        System.out.println(h2.toString());
    }
}
class Hello{}
class Hai extends Object{}

/*
F:\JLC Programs\OOPS\Inheritance\classes>java Lab10
Hello@15db9742
Hai@6d06d69c
*/

Example 7: Cyclical Inheritance is not allowed

class Lab12 
{
    public static void main(String[] args) 
    {
        System.out.println("Hello guys!");
    }
}

class A extends A{}

/*
Lab12.java:9: error: cyclic inheritance involving A
class A extends A
^
1 error
*/

Example 8:

class Lab16 
{
    public static void main(String[] args) 
    {
        Hello hello = new Hello();
        hello.show();
    }
}

class Hai
{
    public int a=10;
    protected int b = 20;
    int c = 30;
}

class Hello extends Hai
{
    void show(){
        System.out.println("public - "+a);
        System.out.println("protected - "+b);
        System.out.println("default - "+c);
    }
}

/*
output:

public - 10
protected - 20
default - 30
*/

Inheritance and Blocks

Example 9 : When sub class has to be loaded, parent class is loaded prior to sub class loading

class Lab18 
{
    public static void main(String[] args) 
    {
        new Hai();
    }
}

class Hello
{
    static int a = 10;
    static{
        System.out.println("Hello S.B a: "+a);
    }
}

class Hai extends Hello
{
    static int b = 20;
    static {
        System.out.println("Hai S.B a:"+a );
        System.out.println("Hai S.B b:"+b);
    }
}

/*
Hello S.B a: 10
Hai S.B a:10
Hai S.B b:20
*/

Example 10: When a super class is called, the sub class is not loaded.

class Lab20 
{
    public static void main(String[] args) 
    {
        System.out.println(Hai.a);
    }
}

class Hai
{
    static int a = 10;
    static{
        System.out.println("Hai SIB a:"+a);
    }
}

class Hello extends Hai
{
    static{
        System.out.println("Hello SIB a:"+a);
    }
}

/*
Hai SIB a:10
10
*/

Example 11: Since the static variable belongs to the parent class, Compiler replaces Hello with Hai. Therefore sub class is not loaded, only the parent class is loaded.

class Lab21
{
    public static void main(String[] args) 
    {
        System.out.println(Hello.a); //Compiler replaces with Hai.a. Therefore, Hello is not loaded
    }
}

class Hai
{
    static int a = 10;
    static{
        System.out.println("Hai SIB a:"+a);
    }
}

class Hello
{
    static{
        System.out.println("Hello SIB a:"+a);
    }
}

/*
Hai SIB a:10
10
*/

Example 12:Order of IIB execution in super class and sub class

class Lab22 
{
    public static void main(String[] args) 
    {
        Hai h = new Hai();
    }
}

class Hello
{
    {
        System.out.println("Hello IIB");
    }
}

class Hai extends Hello
{
    {
        System.out.println("Hai IIB");
    }
}

/*When the above code is executed, this is what compiler does
1. Default no-arg constructor is added by the compiler
2. super() will be the first statement inside the constructor.
3. When Hai object is created, Hai() constructor is called first.
4. super() inside Hai() calls super() of Hello().
5. super() from Hello calls Object class constructor.
6. control comes back to Hello(). Hello IIB is executed.
7. control comes back to Hai(). Hai IIB is executed.


class Hello
{
    Hello(){
        super(); //calls Object class constructor

        //Hello IIB is added below...
        {
            System.out.println("Hello IIB");
        }
    }

}

class Hai
{
    Hai(){
        super(); //calls Hello() constructor

        //Hai IIB is added below...
        {
            System.out.println("Hai IIB");
        }

    }
}

Output:
Hello IIB
Hai IIB
*/

Example 13:

Combination of Static blocks and Instance blocks
class Lab24 
{
    public static void main(String[] args) 
    {
        new Hai();
    }
}

class Hello
{
    {
        System.out.println("Hello IIB");
    }

    static{
        System.out.println("Hello SIB");
    }
}


class Hai extends Hello
{
    {
        System.out.println("Hai IIB");
    }

    static{
        System.out.println("Hai SIB");
    }
}

/*
Hello SIB
Hai SIB
Hello IIB
Hai IIB
*/

Example 14:

class Hai 
{
    public static void main(String[] args) 
    {
        System.out.println("Hai -> main");
    }
    
    static{
        System.out.println("Hai S.B");
    }
}

class Lab25 extends Hai
{
    static{
        System.out.println("Lab25 S.B");
    }
}

/*
Save as Lab25 and run as "java Lab25" : will return the below output.
output:
Hai S.B
Lab25 S.B

If executed as "java Hai"
output:
Hai S.B
Hai -> main
*/

Example 15:

class Lab26 
{
    public static void main(String[] args) 
    {
        Hello.show(); //compiler replaces with Hai.show();
    }
}

class Hai
{
    static void show(){
        System.out.println("Hai -> show()");
    }

    static{
        System.out.println("Hai -> SIB");
    }
}

class Hello extends Hai
{
    static{
        System.out.println("Hello -> SIB");
    }

}
/*
Hai -> SIB
Hai -> show()

*/

Example 16:

When constructors are involved in inheritance.
class Lab28
{
    public static void main(String[] args) 
    {
        new B();
    }
}

class A
{
    A(){
        System.out.println("A()");
    }
}

class B extends A
{
    B(){
        System.out.println("B()");
    }
}

/*
output:

A()
B()
*/

Example 17:

Combination of SIB, IIB, Constructors in Inheritance and their order of execution
class Lab30{
    public static void main(String args[]){
        new C();
    }
}

class A
{
    A()
    {
        System.out.println("A()");
    }

    static{
        System.out.println("A SIB");
    }

    {
        System.out.println("A IIB");
    }
}

class B extends A
{
    B()
    {
        System.out.println("B()");
    }

    static{
        System.out.println("B SIB");
    }

    {
        System.out.println("B IIB");
    }

}

class C extends B
{
    C()
    {
        System.out.println("C()");
    }

    static{
        System.out.println("C SIB");
    }

    {
        System.out.println("C IIB");
    }

}

/*
A SIB
B SIB
C SIB
A IIB
A()
B IIB
B()
C IIB
C()
*/

Summary

  1. Java does not support Multiple Inheritance with classes.
  2. Java supports Multiple Inheritance with interfaces.
  3. Java does not support Hybrid Inheritance which is using multiple inheritance.
  4. Use extends keyword to inherit super class functionalities in sub class.
  5. Only super class members can be accessed by using super class object.
  6. You can access both super and sub class members by using sub class object.
  7. All the super class members can be accessed from sub class directly.
  8. Sub class members cannot be accessed from super class directly.
  9. Object is the default parent class for all Java classes.
  10. When a class is not extending any class then Object class becomes direct super class.
    Example :        class Employee{} //Object is the direct super class.
  11. When a class extends another class, the Object class becomes indirect super class.
    Example:
    class Employee{}
    class Manager extends Manager{} //Object is the indirect super class.
  12. Java doesn't support Cyclic Inheritance.
  13. Cyclic Inheritance happens in two cases:
    1. class A extends A{}
    2. class A extends B{}
      class B extends A{}
  14. final classes cannot be sub classed.
  15. private members of super class will not be inherited to sub class.
  16. When JVM loads the class then:
    1. It checks whether super class is loaded or not.
    2. If super class is not loaded then it loads super class then sub class.
    3. If super class is already loaded, the it loads the sub class directly.
  17. When you access static members of super class using sub class name then subclass will not loaded.
  18. When JVM creates the Object then:
    1. It allocates the memory of instance variables of super class.
    2. It allocates the memory of instance variables of sub class.
    3. It executes the instance blocks and constructors of super class.
    4. It executes the instance blocks and constructors of sub class.
  19. When super class contains main() method then it will be inherited to sub class also i.e you can execute java program either with super class name or subclass name.
  20. Constructors of super class will not be inherited to subclass.
  21. You can use same name fro super class sub class and local variables.
  22. When you access any variable directly then following things will happen:
    1. Checks whether that variable is declared in the local scope or not.
    2. If found int he local scope, that local variable will be used.
    3. If not found in local scope, then checks whether that variable is declared in the class scope or not.
    4. If found, then class level variable will be used.
    5. If not found in the class scope then checks whether that variable is inherited from super classes or not.
    6. If found, that inherited variable will be used.
  23. When you have same name for local variables, class level variables and super class variables then do the following:
    1. Refer the local variable directly.
    2. Refer the class level variable using this keyword.
    3. Refer the super class level variable using super keyword.