Reputation: 16650
I see four alternatives for converting a char
to a Stirng
in Java.
v = Something.lookup(new String((char)binaryData[idx])); // SORRY! Wrong.
v = Something.lookup("" + (char)binaryData[idx]);
v = Something.lookup(String.valueOf((char)binaryData[idx]));
v = Something.lookup(Character.toString((char)binaryData[idx])));
I think that the first is the slowest. The second is very convenient. I speculate that the third may return a previously created String
instance, but I'm not sure, and the API documentation does not say so. The same applies to option four. This reusing of instance would be very fortunate because then a hash based lookup could take advantage of hashCode()
caching in String
. (Which feature is also not described in the API documentation, but many people told me.)
I'm coming from C++ and I feel this lack of complexity informations disturbing. :-) Are my speculations correct? Do we have any kind of official documentation where performance guaranties and the caching mechanisms declared?
Upvotes: 7
Views: 3558
Reputation: 49804
I'm coming from C++ and I feel this lack of complexity informations disturbing. :-) Are my speculations correct? Do we have any kind of official documentation where performance guaranties and the caching mechanisms declared?
To answer this part of the question: in general there isn't. You will find information on the asymptotic performance of built-in collections and maybe a couple of other areas but by and large these issues were left to the VM implementations' discretion. You can of course always look at the source code but bear in mind that there are things that affect performance which you have no direct control over: JIT compiling and garbage collection are the two biggest.
Should you be disturbed by this? I don't think so, Java operates on the premise that low-level performance is rarely an issue the application developer needs to concern herself or himself with. It's a trade-off and you can argue whether it's a good trade-off or not but it is what it is.
But by the time you get to the point where you can develop really high performance systems, you'll have picked up all the necessary information along the way.
Upvotes: 1
Reputation: 26946
The first solution doesn't compile.
The second solution internally creates a String calling a code similar to Character.valueOf(char)
.
Third solution is better than fourth because internal implementation of Character.toString(char ch)
is a call to String.valueOf
public static String toString(char c) {
return String.valueOf(c);
}
Internal implementation of the third String.valueOf(char ch)
is
public static String valueOf(char c) {
char data[] = {c};
return new String(0, 1, data);
}
Upvotes: 1
Reputation: 24464
First of all, the Java specification does not say anything about performance concerning these four methods, hence the results may vary depending on the JRE version and vendor you use.
If you use Oracle's JRE, you can easily inspect the source code by yourself! In Java 8, it is as follows:
Given a char c
with some value:
new String(c)
doesn't compile. No such constructor."" + c
looks ugly, cumbersome and tricky. Internally it creates a new empty StringBuilder
and appends the character to it. Then it creates a new String
instance out of the StringBuilder
.Character.toString(c)
delegates to String.valueOf(c)
.String.valueOf(c)
creates a new String
instance.So which one to use?
The most readable!
That's String.valueOf(c)
or Character.toString(c)
in my point of view!
Upvotes: 10
Reputation: 4812
The second one is certainly(in theory) slower, as it is translated into
v = Something.lookup(new StringBuilder().append("").append((char)binaryData[idx]).toString());
StringBuilder
s are implemented using a char[]
initialized to hold 16 values. The StringBuilder
option therefore initializes a char[]
of size 16, only to copy the cells that are set (only the first one in this case) to the resulting string.
String.valueOf
(which is equivalent to Character.toString
) uses a char[]
of size 1, and then directly sets the String
's backing char[]
, thereby avoiding the need for a copy.
The first approach will not compile (at least not under java 7), as there is no String
constructor accepting a single character as input: http://docs.oracle.com/javase/7/docs/api/java/lang/String.html
Upvotes: 2