Although @Marius' collectFirst
version is probably the most elegant (and maybe a little bit faster as it only uses one closure), I find it more intuitive to use find
for your problem :
def get[A, B](key: A, pairs: List[(A, B)]): Option[B] = pairs.find(_._1 == key).map(_._2)
In case you were wondering (or need high performance), you will need either @Marius' recursive or the following imperative version which may look more familiar (although less idiomatic):
def get[A, B](key: A, pairs: List[(A, B)]): Option[B] = {
var l = pairs
var found: Option[B] = None
while (l.nonEmpty && found.isEmpty) {
val (k, v) = l.head
if (k == key) {
found = Some(v)
} else {
l = l.tail
}
}
found
}
What you must understand is that Option[B]
is a class that may either be instantiated to None
(which replaces and improves the null
reference used in other languages) or Some(value: B)
. Some
is a case class, which allows, among other neat features, to instantiate it without the new
keyword (thanks to some compiler magic, Google Scala case class for more info). You can think of Option
as a List
which may contain either 0 or 1 element: most operations that can be done on sequences can also be applied to Option
s (such as map
in the find
version).