This answer gives an indication that class String
is declared final
for thread safety, which does not convince.
This answer does not convince when it says: And so, you make the classes final. There can be no mutable String, because its an immutable class and its final.
Because,
below field with final
modifier,
/** The value is used for character storage. */
private final char value[];
in class String
would suffice/indicate that data stored in the created object is suppose to be immutable and thread safe.
So, class String
being final
has nothing to do with immutability or thread safety.
But it is not clear, why class String
is declared final
?
Because, as per below class definition, it has final
modifier:
public final class String
implements java.io.Serializable, Comparable<String>, CharSequence
{ .... }
So, class String
cannot be inherited.
Despite field value[]
in class String
is declared final
, additionaly, What is the necessity for class String
also to be final
?
Note: Answers to this question will give an idea behind this design decision
2 Answers 2
You answered your question in your question.
Class String cannot be inherited because it has a final modifier in the class definition. The final modifier does just that in a class definition, declares a class which cannot be inherited from, it has nothing to do with immutability in this case.
The rationale behind this is that a programmer may subclass String therefore have an object which "looks like" a String (i.e. can be passed to methods which take a String argument) however is mutable whereas String is expected to be immutable.
-
I understand that
class String
beingfinal
has nothing to do with immutability. But whyclass String
is declaredfinal
? Of course classes that are final cannot be inherited. But what is the necessity forclass String
to befinal
?overexchange– overexchange2015年06月17日 08:20:17 +00:00Commented Jun 17, 2015 at 8:20 -
-
Can you be more precise on, how subclass designer would treat as mutable? I am not clear with your updated response.overexchange– overexchange2015年06月17日 08:39:43 +00:00Commented Jun 17, 2015 at 8:39
-
@overexchange If String would not be final, I could subclass it and use another mutable (!!) field to store the raw
char[]
, overriding all methods to use that value, which makes it possible to pass an object which is both recognised by the type checker as a String and mutable.11684– 116842015年06月17日 10:44:59 +00:00Commented Jun 17, 2015 at 10:44 -
1Consider the nefarious String subclasses too:
class AlwaysTrueString extends String { public boolean equals(Object o) { return 1; }}
and then pass it into a method somewhere that looks likeboolean passwordMatch(String password)
This would be bad. Being able to reason how String works is important. Having to worry if each String that you dealt with to or from other sources might be designed nefariously makes it much harder for me to write simple code and reason about how that code works.user40980– user409802015年06月17日 13:26:45 +00:00Commented Jun 17, 2015 at 13:26
It doesn't matter that value[] is final when none of the methods on String are not. If string class were not final, I could derive and override all the methods and in effect have a mutable string.
Explore related questions
See similar questions with these tags.
class String
beingfinal
has nothing to do with immutability. But this answer says here:Another reason is thread safety: Immutables are always thread safe
. I think thread safety can be ensured by just making the field ofclass String
asfinal
, but notclass String
asfinal
? 2) Similarly this answer does not make sense to me:And so, you make the ..an immutable class and its final.
String
and he wants to make sure that he knows in before, how its methods are implemented. E.g. he wants to assure that "abc".startsWith("abc") is true and not false because someone has overwritten the method and is not passing aString
but aCustomString
class.