我尝试在Int
上构建一个简单的隐式类来为Ints添加一个函数:
object Helper {
implicit class IntHelper(i: Int) {
def add(str: String): Int = i + str.toInt
}
}
为了更自然地写,我希望DSL允许这个(import Helper._
):
2 add "3" and add "4"
但我无法弄清楚如何执行and
功能。我认为这个会奏效:
object Helper {
implicit class IntHelper(i: Int) {
def add(str: String): Int = i + str.toInt
def and: Int = i
}
}
但没有括号它不起作用(事实上,"2.add("3").and.add("4")
有效,但是对于DSL来说,有太多的句号和圆括号。)
由于
答案 0 :(得分:5)
这个问题是and
现在用作后缀表示法,这通常被建议不要使用,因为它会精确地创建problem with delimiting the expression。所以你可以写
(2 add "3" and) add "4"
但是
2 add "3" and add "4"
大致解析为
2.add("3").and(add)."4"
我建议反对这种DSL。特别是在Scala新手的时候,人们对Scala的表现力很感兴趣,它允许这些DSL,但你必须要质疑它们的价值所在。
如果你真的想要追求这条道路,你可以做出对称的事情。再次将伪and
方法从后缀转换为中缀,添加另一个伪参数,例如then
:
object Helper {
implicit class IntHelper(i: Int) {
def add(str: String): Int = i + str.toInt
}
implicit class AndThen[A](in: A) {
def and(t: then.type): A = in
}
object then
}
import Helper._
2 add "3" and then add "4"
答案 1 :(得分:1)
问题与 0 __ 描述的完全一样。除了 0 __ 的解决方案之外,我还没有看到如何在没有括号的情况下完全实现这一目的。
作为替代方案,这里的版本只需要围绕链式add
调用的括号,这比原始解决方案要少,并且不需要额外的关键字:
object Helper {
implicit class IntHelper(i: Int) {
def add(str: String): Int = i + str.toInt
def and(add: AddWord): Int = i + add.str.toInt
}
val add = AddWord
case class AddWord(private[Helper] val str: String)
}
可以用作:
import Helper._
1 add "3" and add("4") and add("5")