Does it make sense to use pattern matching in Scala with really simple cases?

In “Programming in Scala, Second Edition” on page 410, you can find the Simulation class, which has the following method:

private def next() { (agenda: @unchecked) match { case item :: rest => agenda = rest curtime = item.time item.action() } } 

I'm curious why Odersky implemented this with pattern matching, and not just like that:

 private def next() { val item = agenda.head agenda = agenda.tail curtime = item.time item.action() } 

Is template compatibility so effective that it doesn't even matter? Or was this not a perfect example?

+7
source share
4 answers

Usually I would write it like you do. (Although matching patterns is pretty effective, it's not as effective as head / tail.) If you use

  • Did you want to apply pattern matching
  • You need a MatchException instead of NoSuchElementException
  • In the future you will fill in others.
+9
source

There are several reasons:

  • Part of the book is to make you think about Scala (functional) conditions; pattern matching is the functional programming equivalent.

  • Pattern matching and functional approach are natural patterns in Scala and allow things like concurrency in a natural way; Find out if the template and your Scala programs will be ready for more advanced purposes.

+4
source

Pattern matching is more idiomatic in Scala and more easily protects you from boundary conditions.

In code

 private def next() { val item = agenda.head agenda = agenda.tail curtime = item.time item.action() } 

Both agenda.head and agenda.tail will throw a NoSuchElementException if agenda is an empty list, so for it to actually work you need to add a check for this.

The corresponding version of the template actually has a similar problem (as indicated in the comments), but I will find a fix because all you have to do is add another template:

 private def next() { (agenda: @unchecked) match { case item :: rest => agenda = rest curtime = item.time item.action() case _ => {} } } 
+3
source

My guess is that there is no need to worry about exceptions, there is probably some kind of check before this "next" method is called. Actually, this is probably the reason for the "unverified" annotation, so it really does not need to add additional case _ => . I think the reasoning was more that he wanted to use "unacceptably." An alternative here without pattern matching, but also without head and tail could be something like:

 private def next() { val item :: rest = agenda agenda = rest curtime = item.time item.action() } 
0
source

All Articles