【问题标题】:How can implicits with multiple inputs be used in Scala?如何在 Scala 中使用具有多个输入的隐式?
【发布时间】:2011-01-25 21:09:06
【问题描述】:

例如,如何编写隐式应用以下内容的表达式:

implicit def intsToString(x: Int, y: Int) = "test"

val s: String = ... //?

谢谢

【问题讨论】:

    标签: scala implicit


    【解决方案1】:

    一个参数的隐式函数用于自动将值转换为预期的类型。这些被称为隐式视图。有两个参数,它不起作用或没有意义。

    您可以将隐式视图应用于TupleN

    implicit def intsToString( xy: (Int, Int)) = "test"
    val s: String = (1, 2)
    

    您还可以将任何函数的最终参数列表标记为隐式。

    def intsToString(implicit x: Int, y: Int) = "test"
    implicit val i = 0
    val s: String = intsToString
    

    或者,结合implicit的这两种用法:

    implicit def intsToString(implicit x: Int, y: Int) = "test"
    implicit val i = 0
    val s: String = implicitly[String]
    

    但是在这种情况下它并不是真的有用。

    更新

    要详细说明马丁的评论,这是可能的。

    implicit def foo(a: Int, b: Int) = 0
    // ETA expansion results in:
    // implicit val fooFunction: (Int, Int) => Int = (a, b) => foo(a, b)
    
    implicitly[(Int, Int) => Int]
    

    【讨论】:

    • 您是否暗示(:-))我的原始 def(没有隐式参数列表)不能被隐式调用? (这意味着“隐式”关键字在我的示例中完全没有意义 - 如果没有代码可以观察到差异)。真的是这样吗?或者这是否旨在作为部分答案,在“嘿,至少这些案例有效”的意义上?
    • 正确。我知道在当前语言中可以调用它的方法。编译器警告可能有助于传达这一事实。
    • 原函数不能作为隐式转换,因为它需要两个参数。但是,它仍然可以用作另一种方法的隐式参数。所以 `implicit' 修饰符在这里确实有一个有用的含义。
    • 哇。谢谢马丁,我现在有一种温暖的感觉,在工作中体验了构造的正交性——事实上,所有的函数都是值,所以你说的只有道理。隐式定义也是隐式值。不错。
    • "隐式定义也是隐式值。"我要发推文。 :-)
    【解决方案2】:

    Jason 的回答遗漏了一个非常重要的案例:一个具有多个参数的隐式函数,其中除第一个之外的所有参数都是隐式的……这需要两个参数列表,但考虑到问题的方式,这似乎并没有超出范围表达出来了。

    这是一个带有两个参数的隐式转换示例,

    case class Foo(s : String)
    case class Bar(i : Int)
    
    implicit val defaultBar = Bar(23)
    
    implicit def fooIsInt(f : Foo)(implicit b : Bar) = f.s.length+b.i
    

    REPL 会话示例,

    scala> case class Foo(s : String)
    defined class Foo
    
    scala> case class Bar(i : Int)
    defined class Bar
    
    scala> implicit val defaultBar = Bar(23)
    defaultBar: Bar = Bar(23)
    
    scala> implicit def fooIsInt(f : Foo)(implicit b : Bar) = f.s.length+b.i
    fooIsInt: (f: Foo)(implicit b: Bar)Int
    
    scala> val i : Int = Foo("wibble")
    i: Int = 29
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2012-01-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-01-24
      相关资源
      最近更新 更多