One of the most salient features of our Tech Hiring culture is that there is so much bullshit. Everyone knows this. Each of us contributes his share. But we tend to take the situation for granted.
You are doing benchmark for 100k+ concatenations, and that's fine
But for me, the more interesting result would be: what is the limit for which the performance gap doesn't matter and we should use the cleaner API : String?
I've seen people using StringBuilder to avoid a few concatenation of small strings, and that's for me the pinnacle of premature optimization.
@kaleemniz I agree with Jean-Michel here. Under-the-hood Java's StringBuilder is implemented as a partially filled array. Doing n appends to a partially filled array requires time that is linear in n. On the other hand, concatenating n equal length strings with + requires time that is quadratic in n since each concat requires filling an increasing length array (length 2 then 3 then 4 .... the sum of which is quadratic in n).
So it is no surprise that with huge n like you are using that the StringBuilder is faster. You don't need to time anything for that. Linear time is asymptotically faster than quadratic time. Big-O however hides the effects of low order terms and constants, etc since it is focused on what happens for large inputs.
Microbenchmarks of alternatives with asymptotically different runtimes is far more interesting for smaller input sizes to discover where the break even point is. If n is 2 for example, concatenating the 2 Strings with + is almost certainly faster than the overhead of creating a StringBuilder, as is likely the case for the next few n as well.
But where is the break even point? When does the StringBuilder actually become faster? Your lowest n is 100000. Which for the task, where you are comparing a linear runtime and a quadratic runtime alternative for the same task, may as well be infinity as it doesn't provide any more info than an asymptotic analysis.
I'd be interested to see what you'll find with small n and using a microbenchmarking framework. When is String concatenating with + faster than using StringBuilder and when does StringBuilder become faster?
Rusty polyglot started decades ago with Assembly, Pascal, C, C++ now return to them and Rust after many phases of Java, Python etc. There is something beautiful in simplicity of pure CPU targeted code
Location
Prague, Czech Republic
Work
Lead backend developer somewhere. It just means I'm old
I think this is too general to make any type of rule as every situation is differnet. I'm using simple rule - use your intuition and micro-benchmark particular situation when in doubt ;)
To be little more specific - when I know that I'm adding string contactenation to the code which is guaranteed to be called often hundreds times per second and I'm not too concerned with worse readability, I will optimize the hell out of it. Good example was when I was writing logging wrappers - logging classes will process hundreds of thousands of strings from every part of application so every small piece matters.
But when I'm writing error message strings, email bodies sent from the code which is executed few times a minute I don't care and readability and maintainability is in the driver seat.
And with modern JDK the +/StringBuilder ratio shifted very much to using + sign almost all the time (depends of the type of application obviously).
Those were little bit extreme examples but that's the general way I'm approaching it.
For further actions, you may consider blocking this person and/or reporting abuse
We're a place where coders share, stay up-to-date and grow their careers.
You are doing benchmark for 100k+ concatenations, and that's fine
But for me, the more interesting result would be: what is the limit for which the performance gap doesn't matter and we should use the cleaner API : String?
I've seen people using StringBuilder to avoid a few concatenation of small strings, and that's for me the pinnacle of premature optimization.
This is such a note-worthy point that I did not measure what is the pivot point of n = k where String Builder becomes faster than String.
@kaleemniz I agree with Jean-Michel here. Under-the-hood Java's StringBuilder is implemented as a partially filled array. Doing n appends to a partially filled array requires time that is linear in n. On the other hand, concatenating n equal length strings with + requires time that is quadratic in n since each concat requires filling an increasing length array (length 2 then 3 then 4 .... the sum of which is quadratic in n).
So it is no surprise that with huge n like you are using that the StringBuilder is faster. You don't need to time anything for that. Linear time is asymptotically faster than quadratic time. Big-O however hides the effects of low order terms and constants, etc since it is focused on what happens for large inputs.
Microbenchmarks of alternatives with asymptotically different runtimes is far more interesting for smaller input sizes to discover where the break even point is. If n is 2 for example, concatenating the 2 Strings with + is almost certainly faster than the overhead of creating a StringBuilder, as is likely the case for the next few n as well.
But where is the break even point? When does the StringBuilder actually become faster? Your lowest n is 100000. Which for the task, where you are comparing a linear runtime and a quadratic runtime alternative for the same task, may as well be infinity as it doesn't provide any more info than an asymptotic analysis.
I'd be interested to see what you'll find with small n and using a microbenchmarking framework. When is String concatenating with + faster than using StringBuilder and when does StringBuilder become faster?
I think this is too general to make any type of rule as every situation is differnet. I'm using simple rule - use your intuition and micro-benchmark particular situation when in doubt ;)
To be little more specific - when I know that I'm adding string contactenation to the code which is guaranteed to be called often hundreds times per second and I'm not too concerned with worse readability, I will optimize the hell out of it. Good example was when I was writing logging wrappers - logging classes will process hundreds of thousands of strings from every part of application so every small piece matters.
But when I'm writing error message strings, email bodies sent from the code which is executed few times a minute I don't care and readability and maintainability is in the driver seat.
And with modern JDK the +/StringBuilder ratio shifted very much to using + sign almost all the time (depends of the type of application obviously).
Those were little bit extreme examples but that's the general way I'm approaching it.