The question is in Java why can't I define an abstract static method? for example
abstract class foo {
abstract void bar( ); // <-- this is ok
abstract static void bar2(); //<-- this isn't why?
}
The question is in Java why can't I define an abstract static method? for example
abstract class foo {
abstract void bar( ); // <-- this is ok
abstract static void bar2(); //<-- this isn't why?
}
I believe I have found the answer to this question, in the form of why an interface's methods (which work like abstract methods in a parent class) can't be static. Here is the full answer (not mine)
Basically static methods can be bound at compile time, since to call them you need to specify a class. This is different than instance methods, for which the class of the reference from which you're calling the method may be unknown at compile time (thus which code block is called can only be determined at runtime).
If you're calling a static method, you already know the class where it's implemented, or any direct subclasses of it. If you define
Then any
Foo.bar();
call is obviously illegal, and you will always useFoo2.bar();
.With this in mind, the only purpose of a static abstract method would be to enforce subclasses to implement such a method. You might initially think this is VERY wrong, but if you have a generic type parameter
<E extends MySuperClass>
it would be nice to guarantee via interface thatE
can.doSomething()
. Keep in mind that due to type erasure generics only exist at compile time.So, would it be useful? Yes, and maybe that is why Java 8 is allowing static methods in interfaces (though only with a default implementation). Why not abstract static methods with a default implementation in classes? Simply because an abstract method with a default implementation is actually a concrete method.
Why not abstract/interface static methods with no default implementation? Apparently, merely because of the way Java identifies which code block it has to execute (first part of my answer).
You can't override a static method, so making it abstract would be meaningless. Moreover, a static method in an abstract class would belong to that class, and not the overriding class, so couldn't be used anyway.
As per Java doc:
In Java 8, along with default methods static methods are also allowed in an interface. This makes it easier for us to organize helper methods in our libraries. We can keep static methods specific to an interface in the same interface rather than in a separate class.
A nice example of this is:
instead of
Another example of using static methods is also given in doc itself:
Because 'abstract' means the method is meant to be overridden and one can't override 'static' methods.
The
abstract
annotation to a method indicates that the method MUST be overriden in a subclass.In Java, a
static
member (method or field) cannot be overridden by subclasses (this is not necessarily true in other object oriented languages, see SmallTalk.) Astatic
member may be hidden, but that is fundamentally different than overridden.Since static members cannot be overriden in a subclass, the
abstract
annotation cannot be applied to them.As an aside - other languages do support static inheritance, just like instance inheritance. From a syntax perspective, those languages usually require the class name to be included in the statement. For example, in Java, assuming you are writing code in ClassA, these are equivalent statements (if methodA() is a static method, and there is no instance method with the same signature):
and
In SmallTalk, the class name is not optional, so the syntax is (note that SmallTalk does not use the . to separate the "subject" and the "verb", but instead uses it as the statemend terminator):
Because the class name is always required, the correct "version" of the method can always be determined by traversing the class hierarchy. For what it's worth, I do occasionally miss
static
inheritance, and was bitten by the lack of static inheritance in Java when I first started with it. Additionally, SmallTalk is duck-typed (and thus doesn't support program-by-contract.) Thus, it has noabstract
modifier for class members.You can do this with interfaces in Java 8.
This is the official documentation about it:
https://docs.oracle.com/javase/tutorial/java/IandI/defaultmethods.html