【问题标题】:Why is implicit search impacted by an unrelated type parameter?为什么隐式搜索会受到不相关类型参数的影响?
【发布时间】:2012-02-27 08:42:27
【问题描述】:

考虑一下 Scala 中某些度量单位功能的简化 sn-p:

object UnitsEx {
  case class Quantity[M <: MInt, T: Numeric](value: T) {
    private val num = implicitly[Numeric[T]]
    def *[M2 <: MInt](m: Quantity[M2, T]) = 
      Quantity[M, T](num.times(value, m.value))
  }

  implicit def measure[T: Numeric](v: T): Quantity[_0, T] = Quantity[_0, T](v)
  implicit def numericToQuantity[T: Numeric](v: T): QuantityConstructor[T] = 
    new QuantityConstructor[T](v)

  class QuantityConstructor[T: Numeric](v: T) {
    def m = Quantity[_1, T](v)
  }

  sealed trait MInt
  final class _0 extends MInt
  final class _1 extends MInt
}

这个 sn-p 显示了我目前得到的用法和编译器错误:

import UnitsEx._

(1 m) * 1 // Works
1 * (1 m) // Doesn't work:
/*
<console>:1: error: overloaded method value * with alternatives:
(x: Double)Double <and>
(x: Float)Float <and>
(x: Long)Long <and>
(x: Int)Int <and>
(x: Char)Int <and>
(x: Short)Int <and>
(x: Byte)Int
cannot be applied to (UnitsEx.Quantity[UnitsEx._1,Int])
1 * (1 m)
^
*/

measure 包裹1 可以解决问题,但为什么不应用隐式范围?

如果我像在下一个 sn-p 中那样删除类型参数 M,它就会开始工作,尽管我看不出该类型参数与隐式搜索有何关系:

object UnitsEx2 {   
  case class Quantity[T: Numeric](value: T) {
    private val num = implicitly[Numeric[T]]
    def *(m: Quantity[T]) = Quantity[T](num.times(value, m.value))
  }

  implicit def measure[T: Numeric](v: T): Quantity[T] = Quantity[T](v)
  implicit def numericToQuantity[T: Numeric](v: T): QuantityConstructor[T] = 
    new QuantityConstructor[T](v)

  class QuantityConstructor[T: Numeric](v: T) {
    def m = Quantity[T](v)
  }
}

这是预期的还是类型检查器的已知限制?

【问题讨论】:

标签: scala types compiler-errors implicit-conversion units-of-measurement


【解决方案1】:

如果您将 * 运算符重命名为例如mult 然后 1 mult (1 m) 在这两种情况下都有效。 这并不能回答您的问题,但确实暗示可能对重载的 * 运算符存在一些干扰。

【讨论】:

    猜你喜欢
    • 2021-02-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多