Scala инфиксная нотация с объектом +, почему это невозможно?
Я могу назвать такие объекты, но не могу вызвать m
:
object + {
def m (s: String) = println(s)
}
Нельзя вызвать +.m("hi")
:
<console>:1: error: illegal start of simple expression
+.m("hi")
Также не может вызывать + m "hi"
(предпочтительнее для использования DSL).
Но с object ++
он отлично работает! Вступают ли они в конфликт с (не существующими) методами unary_+
? Можно ли избежать этого?
Ответы
Ответ 1
Действительно, это невозможно с унарными операторами. Если вы хотите называть это в любом случае, вы можете прибегнуть к использованию имени, сгенерированного компилятором для JVM (начинающегося с доллара):
scala> object + {
| def m( s: String ) = println(s)
| }
defined module $plus
scala> +.m("hello")
<console>:1: error: illegal start of simple expression
+.m("hello")
^
scala> $plus.m("hello")
hello
Ответ 2
Я считаю, что проблема заключается в том, что для обработки унарных операторов без двусмысленности scala опирается на частный случай: только !
, +
, -
и ~
рассматриваются как унарные операторы. Таким образом, в +.m("hi")
, scala рассматривают +
как унарный оператор и не могут понять все выражение.
Ответ 3
Другой код с использованием пакета:
object Operator extends App {
// http://stackoverflow.com/info/13367122/scalas-infix-notation-with-object-why-not-possible
pkg1.Sample.f
pkg2.Sample.f
}
package pkg1 {
object + {
def m (s: String) = println(s)
}
object Sample {
def f = {
// +.m("hi") => compile error: illegal start of simple expression
// + m "hi" => compile error: expected but string literal found.
$plus.m("hi pkg1")
$plus m "hi pkg1"
}
}
}
package pkg2 {
object + {
def m (s: String) = println(s)
}
object Sample {
def f = {
pkg2.+.m("hi pkg2")
pkg2.+ m "hi pkg2"
pkg2.$plus.m("hi pkg2")
pkg2.$plus m "hi pkg2"
}
}
}
java version "1.7.0_09"
Scala версия кода 2.9.2