score:25
Standard pattern-matching will always match on only exactly one case. You can get close to what you want by using the fact that patterns can be treated as partial functions (see the Language Specification, Section 8.5, Pattern Matching Anonymous Functions) and by defining your own matching operator, though:
class MatchAll[S](scrutinee : =>S) {
def matchAll[R](patterns : PartialFunction[S,R]*) : Seq[R] = {
val evald : S = scrutinee
patterns.flatMap(_.lift(evald))
}
}
implicit def anyToMatchAll[S](scrut : =>S) : MatchAll[S] = new MatchAll[S](scrut)
def testAll(x : Int) : Seq[String] = x matchAll (
{ case 2 => "two" },
{ case x if x % 2 == 0 => "even" },
{ case x if x % 2 == 1 => "neither" }
)
println(testAll(42).mkString(",")) // prints 'even'
println(testAll(2).mkString(",")) // prints 'two,even'
println(testAll(1).mkString(",")) // prints 'neither'
The syntax is slightly off the usual, but to me such a construction is still a witness to the power of Scala.
Your example is now written as:
// prints both 'foo' and 'bar'
"both" matchAll (
{ case "both" | "foo" => println("foo") },
{ case "both" | "bar" => println("bar") }
)
(Edit huynhjl pointed out that he gave a frighteningly similar answer to this question.)
score:0
One possible way could be:
val a = "both"
a match {
case "foo" => println ("foo") // Case 1
case "bar" => println ("bar") // Case 2
case "both" => println ("foo"); println ("bar")
}
score:1
Just match twice:
val a = "both"
a match {
case "both" | "foo" => println ("foo") // Case 1
}
a match {
case "both" | "bar" => println ("bar") // Case 2
}
score:3
match
executes one, and only one, of the cases, so you can't do this as an or
in the match. You can, however, use a list and map
/foreach
:
val a = "both"
(a match {
case "both" => List("foo", "bar")
case x => List(x)
}) foreach(_ match {
case "foo" => println("foo")
case "bar" => println("bar")
})
And you're not duplicating any of the important code (in this case the println
s).
score:6
At risk of being Captain Obvious, in a case like this it would be simplest just to forget pattern matching and use if
.
if (a == "both" || a == "foo") println("foo")
if (a == "both" || a == "bar") println("bar")
If the repetition of a ==
worries you, you could instead write
if (Set("both", "foo")(a)) println("foo")
if (Set("both", "bar")(a)) println("bar")
using the fact that the apply
method on Set
does the same as contains
, and is a bit shorter.
Source: stackoverflow.com
Related Query
- Pattern matching with more than one match
- Match "fallthrough": executing same piece of code for more than one case?
- scala: convert match statement to pattern matching anonymous function - with values
- Specs2: how to test a class with more than one injected dependency?
- Match more than one element in collection
- Match “fallthrough”: executing same piece of code for more than one case class?
- How to filter a list with a condition that depends on more than one element
- How to initialize a field with more than one operation?
- Functor implementation for types with more than one type
- Can we call method having more than one arguments with list.map?
- Parsing options that take more than one value with scopt in scala
- presentation compiler: type completion in method call with more than one argument
- Spark - after a withColumn("newCol", collect_list(...)) select rows with more than one element
- pattern matching with case match in scala
- matching more than one element from a sequence of elements
- Perform pattern match on a generic value with type matching the return type
- How do I match java.lang.Object with Scala pattern matching
- How to deal with more than one categorical feature in a decision tree?
- Access more than one db with ScalaAnorm with Play
- Match a token that spans more than one line
- wants to read a string if it has more than one value then show in output with single header values seperated by ||
- How do I define Json format for a case class with more than one apply method?
- Why does pattern matching in Scala not work with variables?
- Scala pattern matching on sequences other than Lists
- Pattern matching with conjunctions (PatternA AND PatternB)
- Scala pattern matching confusion with Option[Any]
- What exactly did Scala improve with pattern matching in 2.10?
- How to pattern match a class with multiple argument lists?
- Scala Pattern Matching with Sets
- Scala - pattern matching with conditional statements?
More Query from same tag
- Override abstract type member in stackable trait pattern
- Batch processing in Scala
- Scala using map after a groupBy
- Mongo Spark connector, auth error
- How do I create a periodic Poller with Play 2.0 and Scala
- Why does Gson().toJson() of object with Enumeration throw StackOverflowError?
- Generate functions based on type parameter
- Is it possible for the database to block parallel table accesses in Scala threads?
- how to decompress and read a file containing multiple compressed file in spark
- How to use FXMLLoader?
- About a loss of precision when calculating an aggregate sum with data frames
- Scala - Mutable Map
- How to pass array of array (list of list) to view in play framework 2.x?
- Send tasks to specific executors in Spark
- Extract data between two words using regular expressions in Scala
- Why do we need "Algebraic Data Types"?
- Conditionally filter a sequence
- Problem with Spark DataType Equality for Spark Built in types
- Scala equivalent to Haskell monads
- SCALA - import a trait in a worksheet
- Glue Spark Scala Script to check if file exist in S3?
- Disambiguate constructor parameter with same name as class field of superclass
- Scala GAE project - fail to compile in intellij
- Split string to a 2-dimensional array in Scala
- how to access parent project's classes in sub project in playFramework 2.3.x
- How to change elements of set in scala
- scala how to convert future of one type to future of another type
- SBT installed but not showing in IntelliJ external model list
- I am getting an Invalid syntax while applying filter to my Spark Context (sc)
- Scala: Read a text file and filter on list of values