In Java, it's a common best practice to do string concatenation with StringBuilder due to the poor performance of appending strings using the + operator. Is the same practice recommended for Scala or has the language improved on how java performs its string concatenation?
String concatenation has always been a well-discussed topic among Java developers. It's been costly. Let's first dig into the issue of why it's costly. In Java, string objects are immutable, which means once it is created, you cannot change it.
Let me say the reason that string concatenation is slow is because strings are immutable. This means every time you write "+=", a new String is created. This means the way you build up your string is in the worst case, O(n2).
Using + Operator The + operator is one of the easiest ways to concatenate two strings in Java that is used by the vast majority of Java developers. We can also use it to concatenate the string with other data types such as an integer, long, etc.
In Java, String concatenation forms a new String that is the combination of multiple strings. There are two ways to concatenate strings in Java: By + (String concatenation) operator. By concat() method.
Scala uses Java strings (java.lang.String
), so its string concatenation is the same as Java's: the same thing is taking place in both. (The runtime is the same, after all.) There is a special StringBuilder
class in Scala, that "provides an API compatible with java.lang.StringBuilder
"; see http://www.scala-lang.org/api/2.7.5/scala/StringBuilder.html.
But in terms of "best practices", I think most people would generally consider it better to write simple, clear code than maximally efficient code, except when there's an actual performance problem or a good reason to expect one. The +
operator doesn't really have "poor performance", it's just that s += "foo"
is equivalent to s = s + "foo"
(i.e. it creates a new String
object), which means that, if you're doing a lot of concatenations to (what looks like) "a single string", you can avoid creating unnecessary objects — and repeatedly recopying earlier portions from one string to another — by using a StringBuilder
instead of a String
. Usually the difference is not important. (Of course, "simple, clear code" is slightly contradictory: using +=
is simpler, using StringBuilder
is clearer. But still, the decision should usually be based on code-writing considerations rather than minor performance considerations.)
Scalas String concatenation works the same way as Javas does.
val x = 5
"a"+"b"+x+"c"
is translated to
new StringBuilder()).append("ab").append(BoxesRunTime.boxToInteger(x)).append("c").toString()
StringBuilder is scala.collection.mutable.StringBuilder. That's the reason why the value appended to the StringBuilder is boxed by the compiler.
You can check the behavior by decompile the bytecode with javap.
I want to add: if you have a sequence of strings, then there is already a method to create a new string out of them (all items, concatenated). It's called mkString
.
Example: (http://ideone.com/QJhkAG)
val example = Seq("11111", "2222", "333", "444444")
val result = example.mkString
println(result) // prints "111112222333444444"
Scala uses java.lang.String
as the type for strings, so it is subject to the same characteristics.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With