Consider the following interface :
public interface MyInterface {
public void func1();
public void func2();
abstract public void func3();
}
and the class MyClass :
public class MyClass implements MyInterface{
#Override
public void func1() {
// TODO Auto-generated method stub
}
#Override
public void func2() {
// TODO Auto-generated method stub
}
#Override
public void func3() {
// TODO Auto-generated method stub
}
}
What's the difference between func2() and func3() ?
I must implement both when I want to implement MyClass , so it seems that there's no
difference if I write public or abstract public in the interface .
Thanks
Java 7 and earlier:
There is no difference since all interface methods are public and "abstract." This is implied whether declared or not.
Java 8:
The same rules apply as in Java 7, however, it should be noted that since Java 8, only non-default methods are "abstract." Default methods, are in fact, allowed to have an implementation.
Java 9:
In Java 9, we are provided even more flexibility, and also allowed to have private methods.
Java Language Specification quote:
Every method declaration in the body of an interface is implicitly
abstract, so its body is always represented by a semicolon, not a
block.
You ask
What's the difference between func2() and func3() ?
Except for the fact that they are different methods, their modifiers are the same.
What's the difference between public method and abstract method in Interface?
9.1.1.1. abstract Interfaces
Simply said... none. According to this, it's obsolete.
In a way, we are comparing apples and oranges in this question. For someone new to the Java language, some clarifications need to be made first:
Interfaces:
Interfaces contain method stubs. These are methods without a body.
These methods are implicitly "abstract" and we do not need to explicitly use a modifier to denote this.
That being said, since Java 8, we now have what are called "default methods." These methods are fully implemented methods which do require an explicit declaration using the default keyword.
That being said, the abstract keyword never comes into play in the context of an interface.
Abstract Methods:
Abstract methods only belong in abstract classes.
An abstract class may contain fully implemented methods along with abstract methods. However, just one abstract method in a class is enough to make it an abstract class - That is, the class must be explicitly declared as an abstract class.
An abstract class is a class that is declared abstract—it may or may not include abstract methods. Abstract classes cannot be instantiated, but they can be subclassed.
Related
I'm confused why the following is not allowed:
public interface MyInterface {
MyInterface getInstance(String name);
}
public class MyImplementation implements MyInterface {
public MyImplementation(String name) {
}
#Override
public static MyInterface getInstance(String name) { // static is not allowed here
return new MyImplementation(name)
}
}
I understand why a method in the interface cannot be static, but why can't the overriding method be?
I want all classes to implement the getInstance(String name) method, but I'm currently limited to only being able to call the method if the object has already been instantiated which kind of defeats the purpose...
*update:* Thanks for the answers, I understand it better now. Basically I shouldn't be trying to make a utility class (or a factory class for that matter) implement an interface (or at least, not in this way)...
Invoking static methods in Java requires you to specify the exact type. It is not possible to invoke static methods polymorphically, eliminating the need for #Override.
Please note that this approach is not universal across all languages: for example, you can override class methods in Objective-C, and Apple's cocoa frameworks make good use of this mechanism to customize their "factory" classes. However, in Java, C++, and C# class methods do not support polymorphic behavior.
Theoretically, Java designers could have let you provide interface method implementations through static methods in case an implementation does not need to access the state from the instance. But the same behavior is simple to achieve with a trivial wrapper:
public class MyImplementation implements MyInterface {
public MyImplementation(String name) {
}
#Override
public MyInterface getInstance() { // static is not allowed here
return getInstanceImpl();
}
public static getInstanceImpl() {
return new MyImplementation(name)
}
}
Java compiler could have done the same thing on your behalf, but seeing a static method implement an instance method is both unusual and confusing, so my guess is that Java designers decided against providing this "piece of magic".
Static methods cannot be subject to polymorphic behavior. That would not make much sense. Image this use case, assuming what you want would be possible:
public void foo(MyInterface i) {
i.getInstance("abc");
}
now I want to call this method with an implementation of MyInterface (class A), but since I cannot pass the class itself, I need to pass an object:
A a = new A();
foo(a);
now inside foo the static override of getInstance is called on the instance of class A. So now I am stuck with creating an object just to call a static method.
My point is that you would still be constrained to create an object in most use cases of polymorphism since in your original interface the method was an instance method.
because implementing an interface makes the implementor the type of the interface. That means instances need to have the methods defined by the type, not the class of the instances.
To put it another way,
public void mymethod
and
public static void mymethod
are NOT the same method declaration. They are completely distinct. If mymethod is defined on an interface, having the second definition simply does not satisfy implementing the interface.
The answer comes down to what it means to implement an interface. When a class implements an interface, that is a promise that every instance of the class will respond to every method in the interface. When you implement the method as static, you make it possible to call the method without an instance of the class - but that doesn't fulfill the inheritance implementation's promise that the method will be callable on every instance of the class.
interface Rideable {
String getGait();
}
public class Camel implements Rideable {
int weight = 2;
String getGait() {
return " mph, lope";
}
void go(int speed) {++speed;
weight++;
int walkrate = speed * weight;
System.out.print(walkrate + getGait());
}
public static void main(String[] args) {
new Camel().go(8);
}
}
Upon compiling the above code I've got a compilation error, related to access modifier of getGait() method. Please explain, why should I declare getGait() with public access modifier?
getGait() of Camel implements a method of the Rideable interface. All interface methods are public by default (even if you don't specify it explicitly in the interface definition), so all implementing methods must be public too, since you can't reduce the visibility of the interface method.
In the interface you have method getGait() declared as public. Even you do not state a method as a public in interface it is public.
But in your class, you have declared this method as package private. It is not allowed, because it reduces the visibility of the implemented method.
To avoid this problem. either declare this method as public in your class, or remove declaration (implements Rideable) that your class implements the interface with this method signature.
According object oriented fundamentals, interface contains only public methods. so when you implements interface, you should declare it as a public , otherwise it give you compile time error.
Thanks.
One of the basic usage of interfaces can be to check conformance.For example a class implementing Comparable interface must provide compareTo method and hence providing a mechanism to compare objects of the class.
The reason these methods being public makes sense is that any class which utilizes this conformance must be able to use these methods without any restriction.For example sort method of Arrays class will be good enough to sort objects of a class only if it implements Comparable and exposes the compareTo method(If thats the mechanism you want to provide for sorting.Of course Comparator is also there). So in a nutshell, a contract is only good enough if its readable or usable in case of interfaces(thus making methods public imperative).
In Interface, the fields are implicitly public static final and the methods in an interface are by default public.
Please read the rules of Inheritance:
http://www.codejava.net/java-core/the-java-language/12-rules-of-overriding-in-java-you-should-know
One of which says, "The overriding method must not have more restrictive access modifier". So you are ovveriding the getGait() in Camel class. If you do not provide the access modifier in methods of class then by defaults its default. Which mean you are restricting the access modifier from public to default. Hence breaking the rule of ovveriding which is why its complaining.
Why can't I create a #FunctionalInterface with a default method implementation?
#FunctionalInterface
public interface MyInterface {
default boolean authorize(String value) {
return true;
}
}
You can have default methods in a functional interface but its contract requires you to provide one single abstract method (or SAM). Since a default method have an implementation, it's not abstract.
Conceptually, a functional interface has exactly one abstract method.
Since default methods have an implementation, they are not abstract.
and
If a type is annotated with this annotation type, compilers are
required to generate an error message unless:
The type is an interface type and not an annotation type, enum, or
class.
The annotated type satisfies the requirements of a functional
interface.
Here you don't satisfy the functional interface's requirement, so you need to provide one abstract method. For example:
#FunctionalInterface
interface MyInterface {
boolean authorize(int val);
default boolean authorize(String value) {
return true;
}
}
Note that if you declare an abstract method overriding one of a public method from the Object's class it doesn't count, because any implementation of this interface will have an implementation of those methods through at least the Object's class. For example:
#FunctionalInterface
interface MyInterface {
default boolean authorize(String value) {
return true;
}
boolean equals(Object o);
}
does not compile.
A functional interface is an interface having a single abstract method. The entire purpose of defining functional interfaces is to enable the implementation of the single abstract method via lambda expressions which will effectively override that method which makes providing a default implementation for it pointless.
Having an interface consisting entirely of default methods raises multiple problems. There is the technical problem that the compiler can’t decide for a lambda expression which method to implement when there are multiple default methods and there is the semantic problem that an interface consisting entirely of default methods is not abstract. You can’t instantiate this default behavior as you can’t instantiate interfaces and are forcing programmers to create concrete classes just to invoke the default behavior, which, since interfaces are stateless, could be provided by a singleton instead:
#FunctionalInterface
public interface MyInterface {
static MyInterface DEFAULT = s->true;
boolean authorize(String value);
}
Note that you can have interfaces extending a functional interface and providing a default method, if you need. Still, if this results in creating an interface having no abstract methods I would question the design. You may compare with the discussion about marker interfaces with default methods. If the sub-interface will have different abstract methods than the functional interface, it’s a different story. There might be real use cases for this, but these sub-interfaces will also demonstrate why they shouldn’t be mixed with the functional base interface as a lambda expression will always implement the abstract method.
That's because #FunctionalInterface can have default methods, as many as you want. For example, consider the java.util.Function interface. It contains two default methods: compose and andThen. But there should be exactly one non-default method. Otherwise how compiler would know which of your default methods should be mapped to lambda?
I just want to add a few more points.
We can have any number of Abstract method in FuntionalInterface.
We can also have any number of Static method in FuntionalInterface.
We can also declare an abstract method overriding one of a public method from the Object's class but there must be some other custom abstract method in this functional interface too as shown in below code
#FunctionalInterface
public interface SAM {
public void helloSam();
default void xyz() {
System.out.println("xyz");
}
static void abc() {
System.out.println("abc");
}
static void abc1() {
System.out.println("abc1");
}
default void xyz1() {
System.out.println("xyz1");
}
boolean equals(Object o);
}
We cannot declare abstract methods in interface as protected and default (even if we don't mention any access specifier (default) compiler takes it as public)
but we can declare abstract method in abstract class as protected and default.
Why there are different rules for abstract class and interface?
Because abstract methods of abstract classes are meant to be hooks for subclasses. On the other hand interfaces are not concerned with implementation details - they are only about contracts with the "outside world". And a protected method is an implementation detail.
we cannot declare abstract methods in interface as protected and defaul
the purpose of Interface is to just declare contract. your client will implement it and for that it must be public.
also field in interface are public static final by default,
public you got ,static because it can't be instantiated without implementation and it must not be inherited also.
Update:
as per your question
you want to apply some strict constraint which your implementor can't see ..then what is the use of abstract method in abstract class that must be implemented by any concrete class in the inheritance hierarchy...then no one will be concrete class
public class BaseAbstractClass {
private Connection getConnection(){
//somecode
}
public boolean save(){
//get connection and do something
//return ;
}
//your implementor is left to implement it , he can use save method but can'ge see what it does i mean i doesn't have access to getConnection
public abstract void saveEntity();
}
What is the fragile base class problem in java?
A fragile base class is a common problem with inheritance, which applies to Java and any other language which supports inheritance.
In a nutshell, the base class is the class you are inheriting from, and it is often called fragile because changes to this class can have unexpected results in the classes that inherit from it.
There are few methods of mitigating this; but no straightforward method to entirely avoid it while still using inheritance. You can prevent other classes inheriting from a class by labelling the class declaration as final in Java.
A best practice to avoid the worst of these problems is to label all classes as final unless you are specifically intending to inherit from them. For those to intend to inherit from, design them as if you were designing an API: hide all the implementation details; be strict about what you emit and careful about what you accept, and document the expected behaviour of the class in detail.
A base class is called fragile when changes made to it break a derived class.
class Base{
protected int x;
protected void m(){
x++;
}
protected void n(){
x++; // <- defect
m();
}
}
class Sub extends Base{
protected void m(){
n();
}
}
It is widely described in below article By Allen Holub on JavaWorld
Why extends is evil.
Improve your code by replacing concrete base classes with interfaces
All of what Colin Pickard said is true, but here I want to add some of the best practices when you are writing code that may cause this kind of issue, and especially if you are creating a framework or a library.
Make all your concrete classes final by default, because you probably don't want them to be inherited. You can find this behavior as a feature of many languages, such as Kotlin. Besides, if you need to extend it, you can always remove the final keyword. In this way the absence of final on a class can be interpreted as a warning to not rely on specific functionality for other methods on this that are not private and/or final.
For classes that cannot be marked as final, make as many methods as possible final to ensure they're not modified by subclasses. Additionally, do not expose methods that are not meant to be overridden—prefer private over protected. Assume that any method not private and/or final will be overridden and ensure that your superclass code will still work.
Try to not use an inheritance ("Bar is a Foo") relationship. Instead use a helper ("Bar uses a Foo") relationship between your classes. Use interfaces rather than abstract classes to ensure that classes using this helper have a uniform interface.
Remember that almost* every extends can be replaced by implements. This is true event when you want to have a default implementation; an example of such a conversion is shown below:
Old Code:
class Superclass {
void foo() {
// implementation
}
void bar() {
// implementation
}
}
class Subclass extends Superclass {
// don't override `foo`
// override `bar`
#Override
void bar() {
// new implementation
}
}
New Code:
// Replace the superclass with an interface.
public interface IClass {
void foo();
void bar();
}
// Put any implementation in another, final class.
final class Superclass implements IClass {
public void foo() {
// implementation for superclass
}
public void bar() {
// implementation for superclass
}
}
// Instead of `extend`ing the superclass and overriding methods,
// use an instance of the implementation class as a helper.
// Naturally, the subclass can also forgo the helper and
// implement all the methods for itself.
class Subclass implements IClass {
private Superclass helper = new Superclass();
// Don't override `foo`.
public void foo() {
this.helper.foo();
}
// Override `bar`.
public void bar() {
// Don't call helper; equivalent of an override.
// Or, do call helper, but the helper's methods are
// guaranteed to be its own rather than possibly
// being overridden by yours.
}
}
The advantage of this is that the methods of the superclass are able to be sure they are working with one another, but at the same time you can override methods in your subclass.
*If you actually wanted the superclass to use your overridden method you are out of luck using this approach unless you also want to reimplement all of those methods on the "subclass". That said, the superclass calling the subclass can be confusing so it may be good to reevaluate that type of usage, its incompatibility with this approach notwithstanding.