The answer primarily centers around the use of interfaces and abstract classes.
Let's say you have a block of code:
abstract class testAbstract {
int a; int b; int c;
public String testFunction() {
System.out.println("Override me!");
return "default";
}
public void setValuesByFormula(double a, double b) {
System.out.println("No formula set!");
}
}
This isn't the bet example, but let's say this is intended to allow the user to set a, b, and c from a formula. The user would like to create a new instance of this:
class testClass extends testAbstract {
}
The class testClass currently contains... nothing. But it extends testAbstract and thus has a function setValuesByFormula. When the user tries to call this, however, the system outputs the message: No formula set!
What the user must do at this point is @Override the original function. Thus, the new class becomes:
class testClass extends testInterface {
public void setValuesByFormula(double a, double b) {
//A not really relevant formula goes here.
}
}
This stops the message No formula set! as the user has created their own formula. This is needed for a couple main reasons:
- If a function is inherited from a superclass, often the child will want to override that function. However, the superclass may have default code for its class. Thus, the user must override this function if they wish to use their own code.
- Often, superclasses want to ensure with default code that a certain function will return without error. There are also other instances where default code is helpful. Thus, this provides an alternative: if the user does not need the default code, they can override it.