Scala string FAQ: How do I embed variables in strings in Scala?
A lot of nice new features were added to the Scala language in version 2.10, but a simple feature that makes me happy is string interpolation. This lets Scala developers embed variables inside strings just like you can do in other languages like Perl, PHP, and Ruby — but in an even more powerful way.
Basic solution
To use basic string interpolation in Scala, precede your string with the letter s
and include your variables inside the string, with each variable name preceded by a $
character.
This is shown in the println
statement in the following example:
scala> val name = "Fred" name: String = Fred scala> val age = 33 age: Int = 33 scala> val weight = 200.00 weight: Double = 200.0 scala> println(s"$name is $age years old, and weighs $weight pounds.") Fred is 33 years old, and weighs 200.0 pounds.
According to the official Scala string interpolation documentation, when you precede your string with the letter s
, you’re creating a processed string literal. This example uses the “s string interpolator,” which lets you embed variables inside a string, where they’re replaced by their values. As stated in the documentation, “Prepending s
to any string literal allows the usage of variables directly in the string.”
Using expressions in Scala string literals
In addition to putting variables inside strings, you can include expressions inside a string by placing the expression inside curly braces. According to the official string interpolation documentation, “Any arbitrary expression can be embedded in ${}
.”
In the following example, the value 1
is added to the variable age
inside the string:
scala> println(s"Age next year: ${age + 1}") Age next year: 34
This example shows that you can use an equality expression inside the curly braces:
scala> println(s"You are 33 years old: ${age == 33}") You are 33 years old: true
You’ll also need to use curly braces when printing object fields. The following example shows the correct approach:
scala> case class Student(name: String, score: Int) defined class Student scala> val hannah = Student("Hannah", 95) hannah: Student = Student(Hannah,95) scala> println(s"${hannah.name} has a score of ${hannah.score}") Hannah has a score of 95
Attempting to print the values of the object fields without wrapping them in curly braces results in the wrong information being printed out:
// error: this is intentionally wrong scala> println(s"$hannah.name has a score of $hannah.score") Student(Hannah,95).name has a score of Student(Hannah,95).score
Because $hannah.name
wasn’t wrapped in curly braces, the wrong information was printed; in this case, the toString
output of the hannah
variable.
‘s’ is a method
The s
that’s placed before each string literal is actually a method. Though this seems slightly less convenient than just putting variables inside of strings, there are at least two benefits to this approach:
- Scala provides other off-the-shelf interpolation functions to give you more power.
- You can define your own string interpolation functions.
To see why this is a good thing, let’s look at another string interpolation function.
The ‘f’ string interpolator (printf formatting)
In the example in the Solution, the weight was printed as 200.0
. This is okay, but what can you do if you want to add more decimal places to the weight, or remove them entirely?
This simple desire leads to the “f string interpolator,” which lets you use printf
style formatting specifiers inside strings. The following examples show how to print the weight, first with two decimal places:
scala> println(f"$name is $age years old, and weighs $weight%.2f pounds.") Fred is 33 years old, and weighs 200.00 pounds.
and then with no decimal places:
scala> println(f"$name is $age years old, and weighs $weight%.0f pounds.") Fred is 33 years old, and weighs 200 pounds.
As demonstrated, to use this approach, just follow these steps:
- Precede your string with the letter
f
. - Use printf style formatting specifiers immediately after your variables.
The most common printf
format specifiers are shown in the table in the Discussion.
Though these examples used the println
method, it’s important to note that you can use string interpolation in other ways. For instance, you can assign the result of a variable substitution to a new variable, similar to calling sprintf
in other languages:
scala> val out = f"$name, you weigh $weight%.0f pounds." out: String = Fred, you weigh 200 pounds.
The ‘raw’ interpolator
In addition to the s
and f
string interpolators, Scala 2.10 includes another interpolator named raw
. The raw
interpolator “performs no escaping of literals within the string.”
The following example shows how raw compares to the s interpolator:
scala> s"foo\nbar" res0: String = foo bar scala> raw"foo\nbar" res1: String = foo\nbar
The raw
interpolator is useful when you want to avoid having a sequence of characters like \n
turn into a newline character.
Create your own interpolator
In addition to the s
, f
, and raw
interpolators that are built into Scala 2.10, you can define your own interpolators. See the official Scala String Interpolation documentation for an example of how to create your own interpolator.
Note: String interpolation does not work with pattern-matching statements in Scala 2.10. This feature is planned for inclusion in Scala 2.11.
Discussion
Prior to version 2.10, Scala didn’t include the string interpolation functionality just described. If you need to use a release prior to Scala 2.10 for some reason, the solution is to call the format method on a string, as shown in the following examples:
scala> val name = "Fred" name: java.lang.String = Fred scala> val age = 33 age: Int = 33 scala> val s = "%s is %d years old".format(name, age) s: String = Fred is 33 years old scala> println("%s is %d years old".format(name, age)) Fred is 33 years old
Just as with the string interpolation capability shown in the Solution, you can use this approach anywhere you want to format a string, such as a toString
method:
override def toString: String = "%s %s, age %d".format(firstName, lastName, age)
With either of these approaches, you can format your variables using all the usual printf specifiers. The most common format specifiers are shown here:
Format specifier Description ---------------- --------------------------------- %c Character %d Decimal number (integer, base 10) %e Exponential floating-point number %f Floating-point number %i Integer (base 10) %o Octal number (base 8) %s A string of characters %u Unsigned decimal (integer) number %x Hexadecimal number (base 16) %% Print a “percent” character \% Print a “percent” character
See Also
- My printf cheat sheet shows more format specifiers and examples
- The official Scala String Interpolation documentation
- The Oracle Formatter page
this post is sponsored by my books: | |||
#1 New Release |
FP Best Seller |
Learn Scala 3 |
Learn FP Fast |