Why does CheckStyle suggest that I use a final method? - java

I am using eclipse checkstyle plugin. I have few methods in a class A which are overriden in class B. I have the following warning for most of the methods
The function SearchAndReplace is not conceived to be inherited
- it must be declared abstract or final or leave it empty.
Is there a any advantages to declaring a method as final?
EDIT
I know what the keyword final is for. I know it prevents overriding of methods, is there other advantages, like performance or anything like that?

When you declare a method to be final, you're saying that the method may not be overridden.
Quote from the Java Language Specification:
A method can be declared final to prevent subclasses from overriding or hiding it.
It is a compile-time error to attempt to override or hide a final method.
The common slogan (due to Joshua Bloch I believe) is
"Design and Document for Inheritance or Else Prohibit it"
So, unless your intention is to let subclasses override the method (and potentially change the behavior of the super-class (all methods are virtual in Java)) then make the method final.

A final method guarantees that no subclasses will override the method. Chances are that the runtime can take advantage of this for a performance gain (which may be slight).
The main reason for making a method final is to stop inheritors overriding the method. This might be an important consideration (for example, imagine a method called bool checkSecurity() - letting others override this would be bad!)

In Java, final keyword is applied in various context:
The final keyword is a modifier means the final class can't be extended, a variable can't be modified, and also a method can't be override.

When a method is declared as final it safe to be invoked in constructor(unless other non final methods are invoked in it). If it is not final subclases can override it in a way which tries to access fields introduced in the subclass. And this will often be not what you expect.
i think there is some performence benefit when you write for mobile devices but i am not expert there.

Related

Why does Java allow a constructor to invoke abstract and non-final methods?

Java allows constructors of non-final classes to invoke any instance methods, even if those methods are abstract or non-final.
This is recognized as a bad practice (see., e.g., Effective Java 2nd Edition, Item 17), and isn't possible in C++ because of the defined constructor order.
My question is why this was allowed to begin with in the design of the Java language? It seemed like it could have been forbidden as a language restriction. Are there cases where doing this is necessary?
The Java language allows it because there is (was) no clear, uncontroversial reason to forbid it, specially if you consider that today's Java best practices were not necessarily known at the time the language was originally designed.
Note that a constructor calling an abstract or non-final method does work, because a subclass could override said method, and because the constructor may be executing on a newly-created instance of a subclass (due to constructor execution order from subclass to super class).
As far as I can tell, there is no case where doing it is necessary. But surely some third-party libraries out there do it, even if it is known to be a bad practice.

Why final classes cannot be overridden in java? [duplicate]

This question already has answers here:
What is the point of "final class" in Java?
(24 answers)
Closed 9 years ago.
I was asked about the reason of why a final class cannot be overridden. I tried to explain that it is more of design approach where by you don't want your class to be extended or methods to be overridden and a final class also helps to make an object immutable (though there are more steps to be done rather than just declaring the class as final).
However I would like to know if there is more to thought process behind declaring a class as final or the fact that it cannot be overridden?
Because them's the rules; It's a part of the design of the language.
http://docs.oracle.com/javase/specs/jls/se7/html/jls-8.html#jls-8.1.1.2
As a designer you say "my class is not suitable for inheritence"; Java honours this by explicitly preventing someone from doing so.
Final class cannot be extended because Java compiler will not allow it, because Java compiler follows the rules defined by Java Language Specification which does not allow it.
final methods can't be overriden, because that's what final is designed to do: it's a sign saying "do not override this".
From Wiki
A final method cannot be overridden or hidden by subclasses. This is used to prevent unexpected behavior from a subclass altering a method that may be crucial to the function or consistency of the class.
A common misconception is that declaring a class or method as final improves efficiency by allowing the compiler to directly insert the method wherever it is called (see inline expansion). But because the method is loaded at runtime, compilers are unable to do this. Only the runtime environment and JIT compiler know exactly which classes have been loaded, and so only they are able to make decisions about when to inline, whether or not the method is final.
A final class is a class that can't be extended, thats the reason u cannot override the final class
it is also used to make the class immutable
and one good advantage of defining class as final that it improves JVM performance
see this

When I define an interface method's parameters final do I need to repeat final in the implementations? [duplicate]

This question already has answers here:
Final arguments in interface methods - what's the point?
(5 answers)
Closed 9 years ago.
So do I need to repeat final in the case below ?
interface Foo {
void meth(final Bar bar);
}
public Baz implements Foo {
#Override
void meth(/* is it final ?*/ Bar bar){}
}
The question is not only for interface inheritance but class inheritance also - I guess the answer will be the same
Yes you do need to redeclare method parameters as final if you want the compiler to make sure these parameters are never reassigned in the current method. This holds both when overriding interface and class definitions.
The reason for this is rather simple: This is the behavior specified in the Java language specification. However, the compiler could not even check for not reassigning final parameters even if it wanted to:
The final modifier for variables in method scope is actually not translated into byte code or written elsewhere into the Java class file format. It basically disappears after the compilation of a specific class or interface and cannot be traced after this compilation. Since each class and interface is compiled independently of other classes and interfaces, the compiler or the JVM run time verifier could not make sure that final parameters were assigned with a new value in subclasses or interface implementations. It is only within the compilation of a single class where the Java compiler can assure that such assignments do not occure. The declaration of final parameters is therefore local for a class and it would not be possibility to change this behavior in the future or to find out about this feature by using run time reflection.
Using a final parameter in an abstract method signature does therefore not serve a purpose, neither a real one or a documentary one: Since Java implements method calls by call by value and not by reference, the final modifier will never effect code outside of the implementing method's scope. If a method parameter variable is reassigned is therefore merely a detail of the methods actual implementation. I would therefore personally never use it for defining abstract methods in classes or interfaces. It is allowed but meaningless.
Within non-abstract method definitions, declaring a method variable final only serves one of two purposes:
You want to use a variable inside an anonymous class's scope.
You want the compiler to check that you did not accidentaly reassign a variable. This is escpecially useful when dealing with many variables of similar type. Here, the final modifier also serves as some kind of documentation.
UPDATE: Since Java 8, a method parameter is attributed on if it is synthetic (non represented in the source code, mandated (implicitly present in the source code, e.g. the this reference for lambda expressions) or if it is final. This does however not effect overridden methods where the final declaration needs to be repeated for this flag to be set. Furthermore does the Java language not pay attention to these flags, it is only meta frameworks that read these flags to implement their logic which might react to theses flags.

Why is it that we cannot override static and final methods? [duplicate]

This question already has answers here:
Why doesn't Java allow overriding of static methods?
(22 answers)
Closed 9 years ago.
I am trying to understand why we can't override static and final methods. I do not get the purpose behind it.
final methods can't be overriden, because that's what final is designed to do: it's a sign saying "do not override this".
static methods can't be overriden, because they are never called in a polymorphic way: when you call SomeClass.foo() it will always be the foo method of SomeClass, no matter if there is another ExtendedSomeClass that has a much groovier foo method.
final is used to avoid overriding. And a static method is not associated with any instance of a class so the concept is not applicable.
The reason for not overriding static method is that Static methods are treated as global by the JVM so there are not bound to an object instance at all. Similarly final methods cant be overriddent because when you say a method as final then it mean you are saying to the JVM that this method cannot be overridden.
The wiki has a very important misconception about final. Do read that!
A final method cannot be overridden or hidden by subclasses.[2] This
is used to prevent unexpected behavior from a subclass altering a
method that may be crucial to the function or consistency of the
class.[3]
A common misconception is that declaring a class or method as final
improves efficiency by allowing the compiler to directly insert the
method wherever it is called (see inline expansion). But because the
method is loaded at runtime, compilers are unable to do this. Only the
runtime environment and JIT compiler know exactly which classes have
been loaded, and so only they are able to make decisions about when to
inline, whether or not the method is final.[4]
Static methods are covered here.
Final methods cannot be overridden because the purpose of the "final" keyword is to prevent overriding.
Final cannot be overridden because that is the purpose of the keyword, something that cannot be changed or overridden.
The purpose of inheritance and polymorphism is to have objects of same class implementing methods (not the names but the code in the methods) in different ways. And static methods cannot be accessed by objects because they are a part of the class not the instance. So there is no purpose to overriding the Static methods. And you can have a static method in subclass by the same name but that won’t be an overridden method.
If you haven't yet read about Inheritance and Polymorphism which are both features of Java, you should and also try to write the code in the question so that SO users can answer with an example.

FindBugs wants readObject(...) to be private for serialization, why?

I am running findbugs on some code and it says the readObject(...) method must be private to be invoked for serialization/unserialization? Why? What is the problem if it is made public?
About readObject()/writeObject() being private, here's the deal: if your class Bar extends some class Foo; Foo also implements readObject()/writeObject() and Bar also implements readObject()/writeObject().
Now, when a Bar object is serialized or deserialized, JVM needs to call readObject()/writeObject() for both Foo and Bar automatically (i.e. without you needing to call these super class methods explicitly). However, if these methods are anything but private, it becomes method overriding, and JVM can no longer call the super class methods on the sub class object.
Hence they must be private!
In the modern Java implementations (at least JDK 6 through 10), the ObjectInputStream and ObjectOutputStream classes will only recognize readObject, readObjectNoData and writeObject methods if they are declared as private and NOT static.
(I couldn't find this stated explicitly in any of the documentation, but the restriction is clearly implemented in the code.)
So, irrespective of whether it is a good idea or not, FindBugs is correct in pointing out that a non-private readObject method is a bug. It won't be used.
The only reason I want to make this method public is to make it final so that inheriting objects cannot fiddle with it.
I don't think you should try to do that. Put a note in the class-level javadoc to say what you think that subclasses should and should not do. If someone chooses to implement a class ignoring that advice, it is their problem to deal with the consequences.
The problem with trying to force other people to implement subclasses in a particular way is that they may have a use-case that requires them to do things differently ... for reasons that you are not in a position to understand. It is a better idea to leave future developers with the freedom to do what they want, and let them take responsibility for the consequences.
I'm not sure why findbugs thinks it's a bug, but I can guess at two possible reasons. Making readObject public breaks encapsulation because the calling code has visibility into the internal structure of your class. Also, by making it public you force all derived classes to declare readObject as public. So unless the class is final, you're changing the contract for serialization.
I thought findbugs could provide rationale for most of its messages. Does it have anything to say about this?
There's no reason for you to call serialization methods such as readObject yourself, much less from another class. You should minimize the visibility of everything you can.
Edit: If you want subclasses to be able to change the behavior, make the method protected... that's acceptable.
In order for your method to be called by objectInputStream.readObject(), you must declare it private:
private void readObject(ObjectInputStream objectInputStream)
If you do not, your method will not be called (put a break point in there to prove this). Your code may appear to work but that is because the default serialization is being used.
You might be wanting to make this protected to allow for subclassing but this is not needed. The serialization process automatically calls the readObject of the base class prior to calling the readObject of the concrete class. This happens even if the concrete class does not make a call to:
objectInputStream.defaultReadObject();
...contrary to other posts I have read on the web. The same applies to the writeObject methods as well.

Categories

Resources