Rakesh
Rakesh

Reputation: 53

Java Inheritance strange behaviour

The following code prints output as 40 instead of 30. I'm not able to figure out the solution. Please help with the code.

class Base {

  int value = 0;

    Base() {
      addValue();
    }

    void addValue() {
      value += 10;
    }

    int getValue() {
      return value;
    }
}

class Derived extends Base {

  Derived() {
    addValue();
  }

  void addValue() {
    value +=  20;
  }
}

public class Test{

  public static void main(String[] args) {
    Base b = new Derived();
    System.out.println(b.getValue());
  }
}

  The implicit super reference in Derived constructor calls Base constructor which in turn calls method addValue() in the class Base results in value variable as 10 and then addValue() in the Derived class should add 20 to value 10. So the final output is 30.

But the code prints 40.

Upvotes: 5

Views: 226

Answers (6)

Tom Hawtin - tackline
Tom Hawtin - tackline

Reputation: 147154

As others have got there before me: addValue is overridden in Derived, as it is an accessible method with the same name and same parameter types. Typically you would add the @Override annotation to the override method. The method in the derived class even though the base class is still under construction.

Not all languages do the same thing. C++, for example, will not run overridden methods from derived class whilst the base constructor is still running. The equivalent program in C++ does show 30.

#include <iostream>

class Base {
public:
    int value;

    Base() : value(0) {
      addValue();
    }

    virtual void addValue() {
      value += 10;
    }

    int getValue() {
      return value;
    }
};

class Derived : public Base {
public:
  Derived() {
    addValue();
  }

  virtual void addValue() {
    value +=  20;
  }
};

int main() {
    Base *b = new Derived();
    std::cout << b->getValue() << std::endl;
}

Upvotes: 1

Navarasu
Navarasu

Reputation: 8479

As others discussed earlier Method Overriding property applies to method call in the base class well.

By this java applies Run Time Polymorphism i.e., Based on the object that is invoked at run time, the method which is to be executed is decided. For e.g.,

  • If super class object is used to invoke the method, then super class method will be executed.
  • If sub class object is used to invoke the method, then sub class method will be executed.

If we don't want to override, we can make the parent method as private instead of default private package. Now we will be getting 30 as output. As the method which cannot be inherited then it cannot be overridden

class Base {

    int value = 0;

    Base() {
        addValue();
    }

    private void addValue() {
        value += 10;
    }

    int getValue() {
        return value;
    }
}

class Derived extends Base {

    Derived() {
        addValue();
    }

    void addValue() {
        value +=  20;
    }
}

public class Test{

    public static void main(String[] args) {
        Base b = new Derived();
        System.out.println(b.getValue());
    }
}

Now, the output is 30.

Upvotes: 0

Khalid Shah
Khalid Shah

Reputation: 3232

addValue() is override in Derived class and you created a Derived class object. So whenever the addValue() called by this instance. Always methos is called of Derived class. So thats why addValue() of Derived class called twice. Once in the Base class constructor and second in Derived class constructor.

Upvotes: 0

Rarblack
Rarblack

Reputation: 4664

Most probably when you extend the Base class

class Derived extends Base {

  Derived() {

    addValue();

  }

  void addValue() { //here

    value +=  20;

  }

}

you put the method name same in the Base Class and this overrides the default one which is:

   void addValue() {
      value += 10;
    }

So, the output is 40 -> 20 + 20

Upvotes: 2

ControlAltDel
ControlAltDel

Reputation: 35011

In class Derived, the method void addValue() points to the method defined in Derived, not in Base

Upvotes: 4

yole
yole

Reputation: 97148

The addValue method is overridden in the Derived class. When a method is overridden, calling a method on an instance of this class always calls the overridden version, even when the call happens in the base class.

Upvotes: 8

Related Questions