Omitting parenthesis - scala

Here is Scala code
#1
def method1 = {
map1.foreach({
case(key, value) => { println("key " + key + " value " + value) }
})
}
#2
def method1 = {
map1.foreach{
case(key, value) => { println("key " + key + " value " + value) }
}
}
It almost figures for me, but nevertheless I want to make it clearer: why is it possible to omit parenthesis in this case?

You can always exchange methods argument parentheses for curly braces in Scala. For example
def test(i: Int) {}
test { 3 }
The base for this is the definition of argument expressions, covered by section §6.6 of the Scala Language Specification (SLS):
ArgumentExprs ::= ‘(’ [Exprs] ‘)’
| ‘(’ [Exprs ‘,’] PostfixExpr ‘:’ ‘_’ ‘*’ ’)’
| [nl] BlockExpr
The curly braces are covered by the last case (block expression), which essentially is ‘{’ Block ‘}’ (cf. beginning of chapter 6 SLS).
This doesn't go for conditional expressions, if, (§6.16 SLS) and while loop expressions (§6.17 SLS), but it works for for comprehensions (§6.19 SLS), somewhat of an inconsistency.
A pattern matching statement or pattern matching anonymous functions literal on the other hand must be defined with curly braces, e.g. { case i: Int => i + i }, parentheses are not allowed here (§8.5 SLS).
In your method call, foreach takes a function argument, so you can drop the redundant parentheses or double braces:
List(1, 2).foreach({ case i => println(i) })
List(1, 2).foreach {{ case i => println(i) }}
List(1, 2).foreach { case i => println(i) } // no reason to have double braces
In this case, the pattern matching doesn't really buy you anything, and you can use a regular (non-pattern-matching) function, and thus the following would work, too:
List(1, 2).foreach(i => println(i)) // §6.23 SLS - anonymous functions
List(1, 2).foreach(println) // §6.26.2 / §6.26.5 - eta expansion
In your case though, a Map's map method passes a tuple of key and value to the function, that's why you use pattern matching (case statements) to deconstruct that tuple, so you are bound to have curly braces. That is nicer than writing
map1.foreach(tup => println("key " + tup._1 + " value " + tup._2)
As a side note, putting braces around pattern matching case bodies is considered bad style; they are not necessary, even if the body spans multiple lines. So instead of
case(key, value) => { println("key " + key + " value " + value) }
you should write
case (key, value) => println("key " + key + " value " + value)
There is a bit of polemic in this blog post regarding the different variants of using braces, dots and parentheses in Scala (section "What's not to like"). In the end, you are to decide which is the best style—this is where people advocating "opinionated" versus "un-opinionated" languages fight with each other.
In general, you need curly braces when the expression spans multiple lines or if you have a pattern match. When calling methods with multiple parameter lists, often the last list contains one function argument, so you get nice looking—subjective judgment of course—syntax:
val l = List(1, 2, 3)
l.foldLeft(0) {
(sum, i) => sum + i
}

Related

Trying to understand scala ^^ syntax

I'm beginner in scala and looking at this tutorial :
http://enear.github.io/2016/03/31/parser-combinators/
Event it is explained just below :
The ^^ operator acts as a map over the parse result. The regex
"[a-zA-Z_][a-zA-Z0-9_]*".r is implicitly converted to an instance of
Parser[String], on which we map a function (String => IDENTIFIER),
thus returning a instance of Parser[IDENTIFIER].
I dont understand this code snippet :
def identifier: Parser[IDENTIFIER] = {
"[a-zA-Z_][a-zA-Z0-9_]*".r ^^ { str => IDENTIFIER(str) }
}
Can someone explain the ^^ operator and how it is mapped to a block code ?
Thanks
It defines the operation that needs to be performed when the left-hand side expression is evaluated.
For instance, we have some code like this:
def symbol: Parser[Any] = "+" | "-" | "*"
def number: Parser[Int] = """(0|[1-9]\d*)""".r ^^ {string => string.toInt }
def expression = {
number ~ symbol ~ number ^^ { case firstOperand ~ operator ~ secondOperand =>
firstOperand + secondOperand
}
}
So, here in the number we will convert String to Int. This means that when we will use our parser like this:
parse(expression, "3 + 2")
It will return us 5, if we will not convert it and leave it as Strings we will get "32".

Scala: Operator Pattern Matching

Is it possible in Scala to do pattern matching with an operator?
I want to input a tuple, for example ("Hello World", +) or ("Good Afternoon", /) and do different actions for different operators, like:
mytuple match {
case (SomeRegex(str), +) => println(str + " the same")
case (SomeRegex(str), /) => println(str + " but different")
}
How can I correctly do this? I don't care what the operators do, I just want them as a kind of environment.
Maybe even passing the char +or / along is considered best practice, but I hardly believe it.
Where would the + and * be coming from? And what would the type of mytuple be?
Depending on your answer to those, this might be a reasonable answer.
The language doesn't really expose * and + as objects (at least not in the way it seems like you're aiming for).
sealed trait Op
case object `+` extends Op
case object `*` extends Op
// ...
With those definitions in hand...
def dispatch(mytuple: (String, Op)): Unit =
mytuple match {
case (SomeRegex(str), `+`) => println(str + " the same")
case (SomeRegex(str), `*`) => println(str + " but different")
case _ => ()
}
You can treat + and * (or any other string that the parser might have treated otherwise: def type class some identifier with spaces) as regular identifiers by wrapping them in `'s.

How to pattern match on List('(', List[Char],')')?

I am struggling a bit with some pattern matching on a List[Char]. I would like to extract sub-lists that are enclosed by parentheses. So, I would like to extract "test" as a List[Char] when given "(test)". So basically a match on List('(', List[Char],')'). I am able to match on List('(',t,')') where t is a single character, but not a variable amount of characters.
How should this be declared?
val s = "(test)"
s match {
case List('(',t,')') => {
println("matches single character")
}
case '('::x::y => {
//x will be the first character in the List[Char] (after the '(') and y the tail
}
}
s match {
case '(' +: t :+ ')' => ...
}
Read about custom extractors in Scala and then see http://www.scala-lang.org/api/2.11.8/index.html#scala.collection.$colon$plus$ to understand how it works.
Note that it'll match any suitable Seq[Char], but a string isn't really one; it can only be converted (implicitly or explicitly). So you can use one of
val s: Seq[Char] = ...some String or List[Char]
val s = someString.toSeq
I expect that performance for String should be good enough (and if it's critical, don't use this); but for large List[Char] this will be quite slow.

scheme cond in scala language

Does scala have an equivalent to scheme's cond?
I guess you're looking for match (or just simply if/else if/else).
case class Paired(x: Int, y: Int)
def foo(x: Any) = x match {
case string : String => println("Got a string")
case num : Int if num < 100 => println("Number less than 100")
case Paired(x,y) => println("Got x and y: " + x + ", " + y)
case unknown => println("??: " + unknown)
}
The first two case statements show type based pattern matching. The third shows the use of an Extractor to break data down into constituent parts and to assign those parts to variables. The third shows a variable pattern match which will match anything. Not shown is the _ case:
case _ => println("what")
Which like the variable pattern match, matches anything, but does not bind the matched object to a variable.
The case class at the top is Scala shorthand for creating an extractor as well as the class itself.
Of course, neither match nor if does exactly the same thing as cond. One possibility is to do like this:
object Cond {
def apply(clauses: Iterable[(()=>Boolean, ()=>Any)]): Any = {
clauses find (_._1()) map (_._2()) getOrElse ()
}
}
This object accepts something Iterable where each item is a pair of a function returning Boolean and a function returning Any. It tries to find an item whose first function returns true, stops looking if it finds one, calls the second function on a found item and returns the result of that function (or () if none was found).
Examples:
val clauses = Seq(
({()=>false}, {()=>println("foo")}),
({()=>true}, {()=>println("bar")})
)
Cond(clauses)
def checkYear(year: Int) = {
Cond(Seq(
({()=>year % 400 == 0}, {()=>42}),
({()=>true}, {()=>{c:Char => (c.toString * 3)}})
))
}
ETA: Yes, I know it is ugly, but it works.
The most straightforward translation is to use pattern guards, although it requires some boilerplate. Pattern guards only work in a case pattern, and case only works in a match (unless we're writing a PartialFunction).
We can satisfy these conditions by matching a unit value against trivial cases:
;; Scheme
(cond
(foo bar)
(baz quux)
(t mydefault))
// Scala
() match {
case _ if foo => bar
case _ if baz => quux
case _ => mydefault
}

Explain this pattern matching code

This code is from Querying a Dataset with Scala's Pattern Matching:
object & { def unapply[A](a: A) = Some((a, a)) }
"Julie" match {
case Brothers(_) & Sisters(_) => "Julie has both brother(s) and sister(s)"
case Siblings(_) => "Julie's siblings are all the same sex"
case _ => "Julie has no siblings"
}
// => "Julie has both brother(s) and sister(s)"
How does & actually work? I don't see a Boolean test anywhere for the conjunction. How does this Scala magic work?
Here's how unapply works in general:
When you do
obj match {case Pattern(foo, bar) => ... }
Pattern.unapply(obj) is called. This can either return None in which case the pattern match is a failure, or Some(x,y) in which case foo and bar are bound to x and y.
If instead of Pattern(foo, bar) you did Pattern(OtherPattern, YetAnotherPatter) then x would be matched against the pattern OtherPattern and y would be matched against YetAnotherPattern. If all of those pattern matches are successful, the body of the match executes, otherwise the next pattern is tried.
when the name of a pattern is not alphanumeric, but a symbol (like &), it is used infix, i.e. you write foo & bar instead of &(foo, bar).
So here & is a pattern that always returns Some(a,a) no matter what a is. So & always matches and binds the matched object to its two operands. In code that means that
obj match {case x & y => ...}
will always match and both x and y will have the same value as obj.
In the example above this is used to apply two different patterns to the same object.
I.e. when you do
obj match { case SomePattern & SomeOtherPattern => ...}`
first the pattern & is applied. As I said, it always matches and binds obj to its LHS and its RHS. So then SomePattern is applied to &'s LHS (which is the same as obj) and SomeOtherPattern is applied to &'s RHS (which is also the same as obj).
So in effect, you just applied two patterns to the same object.
Let's do this from the code. First, a small rewrite:
object & { def unapply[A](a: A) = Some(a, a) }
"Julie" match {
// case Brothers(_) & Sisters(_) => "Julie has both brother(s) and sister(s)"
case &(Brothers(_), Sisters(_)) => "Julie has both brother(s) and sister(s)"
case Siblings(_) => "Julie's siblings are all the same sex"
case _ => "Julie has no siblings"
}
The new rewrite means exactly the same thing. The comment line is using infix notation for extractors, and the second is using normal notation. They both translate to the same thing.
So, Scala will feed "Julie" to the extractor, repeatedly, until all unbound variables got assigned to Some thing. The first extractor is &, so we get this:
&.unapply("Julie") == Some(("Julie", "Julie"))
We got Some back, so we can proceed with the match. Now we have a tuple of two elements, and we have two extractors inside & as well, so we feed each element of the tuple to each extractor:
Brothers.unapply("Julie") == ?
Sisters.unapply("Julie") == ?
If both of these return Some thing, then the match is succesful. Just for fun, let's rewrite this code without pattern matching:
val pattern = "Julie"
val extractor1 = &.unapply(pattern)
if (extractor1.nonEmpty && extractor1.get.isInstanceOf[Tuple2]) {
val extractor11 = Brothers.unapply(extractor1.get._1)
val extractor12 = Sisters.unapply(extractor1.get._2)
if (extractor11.nonEmpty && extractor12.nonEmpty) {
"Julie has both brother(s) and sister(s)"
} else {
"Test Siblings and default case, but I'll skip it here to avoid repetition"
}
} else {
val extractor2 = Siblings.unapply(pattern)
if (extractor2.nonEmpty) {
"Julie's siblings are all the same sex"
} else {
"Julie has no siblings"
}
Ugly looking code, even without optimizing to only get extractor12 if extractor11 isn't empty, and without the code repetition that should have gone where there's a comment. So I'll write it in yet another style:
val pattern = "Julie"
& unapply pattern filter (_.isInstanceOf[Tuple2]) flatMap { pattern1 =>
Brothers unapply pattern1._1 flatMap { _ =>
Sisters unapply pattern1._2 flatMap { _ =>
"Julie has both brother(s) and sister(s)"
}
}
} getOrElse {
Siblings unapply pattern map { _ =>
"Julie's siblings are all the same sex"
} getOrElse {
"Julie has no siblings"
}
}
The pattern of flatMap/map at the beginning suggests yet another way of writing this:
val pattern = "Julie"
(
for {
pattern1 <- & unapply pattern
if pattern1.isInstanceOf[Tuple2]
_ <- Brothers unapply pattern1._1
_ <- Sisters unapply pattern1._2
} yield "Julie has both brother(s) and sister(s)
) getOrElse (
for {
_ <- Siblings unapply pattern
} yield "Julie's siblings are all the same sex"
) getOrElse (
"julie has no siblings"
)
You should be able to run all this code and see the results for yourself.
For additional info, I recommend reading the Infix Operation Patterns section (8.1.10) of the Scala Language Specification.
An infix operation pattern p op q is a
shorthand for the constructor or
extractor pattern op(p,q). The
precedence and associativity of
operators in patterns is the same as
in expressions.
Which is pretty much all there is to it, but then you can read about constructor and extractor patterns and patterns in general. It helps separate the syntactic sugar aspect (the "magic" part of it) from the fairly simple idea of pattern matching:
A pattern is built from constants,
constructors, variables and type
tests. Pattern matching tests whether
a given value (or sequence of values)
has the shape defined by a pattern,
and, if it does, binds the variables
in the pattern to the corresponding
components of the value (or sequence
of values).