This is an excerpt from the 1st Edition of the Scala Cookbook (partially modified for the internet). This is a short recipe, Recipe 19.2, “How to write a Scala method that takes a simple generic type.”
Problem
You’re not concerned about type variance, and want to create a Scala method (or function) that takes a generic type, such as a method that accepts a Seq[A]
parameter.
Solution
As with Scala classes, specify the generic type parameters in brackets, like [A]
. For example, when creating a lottery-style application to draw a random name from a list of names, you might follow the “Do the simplest thing that could possibly work” credo, and initially create a method without using generics:
def randomName(names: Seq[String]): String = { val randomNum = util.Random.nextInt(names.length) names(randomNum) }
As written, this works with a sequence of String
values:
val names = Seq("Aleka", "Christina", "Tyler", "Molly") val winner = randomName(names)
Then, at some point in the future you realize that you could really use a general-purpose method that returns a random element from a sequence of any type. So, you modify the method to use a generic type parameter, like this:
def randomElement[A](seq: Seq[A]): A = { val randomNum = util.Random.nextInt(seq.length) seq(randomNum) }
With this change, the method can now be called on a variety of types:
randomElement(Seq("Aleka", "Christina", "Tyler", "Molly")) randomElement(List(1,2,3)) randomElement(List(1.0,2.0,3.0)) randomElement(Vector.range('a', 'z'))
Note that specifying the method’s return type isn’t necessary, so you can simplify the signature slightly, if desired:
// change the return type from ':A =' to just '=' def randomElement[A](seq: Seq[A]) = { ...
this post is sponsored by my books: | |||
#1 New Release |
FP Best Seller |
Learn Scala 3 |
Learn FP Fast |
Discussion
This is a simple example that shows how to pass a generic collection to a method that doesn’t attempt to mutate the collection. See Recipes 19.4 and 19.5 for more complicated situations you can run into.