【问题标题】:Extension Method for Map in ScalaScala中Map的扩展方法
【发布时间】:2016-04-03 14:48:06
【问题描述】:

我是 Scala 世界的新手! 我正在尝试开发一些帮助程序,以使我的 Scala 代码生活更轻松。 例如,我试图让它工作的部分如下 -

object Helpers{
  implicit class MapExt(val self: Map[String, Any]) extends AnyVal {
      // gets a map value for specified key casting as required type
      def GetValueAs[T](key: String): T = self(key).asInstanceOf[T];
  }
}

这段代码背后的逻辑是我有一个StringAny 的映射,我需要在运行时转换值。我在这里想要实现的目标并不重要,但重要的是我们如何在 Scala 中做到这一点。我如何才能拥有适用于特定类型的泛型类型(在本例中为 Map[String, Any])的扩展方法,并且该方法本身就是泛型类型。如果我尝试将上面的代码用作 -

,上面的代码会给我一个编译时错误
myMap.GetValueAs[Date]("start_date")

错误:值 GetValueAs 不是 scala.collection.immutable.Map[String,Any] 的成员

有人可以帮助让他的简单示例起作用。这将是一个很大的帮助,我很感激!

谢谢

【问题讨论】:

  • 它对我有用。您是否将隐式类纳入范围。 IE。你在打电话给myMap.GetValueAs 之前import Helpers._ 了吗?这应该就是所需要的。
  • 你为什么有extends AnyVal?这有意义吗,即在这种情况下你会享受它的好处吗?
  • 我们在 Scala 中不将方法名大写。改用getValueAs
  • 因为我在同一个范围内,我认为它会自动完成,但显然它没有:(感谢帮助
  • @KevinMeredith 基于 Scala 文档,如果您不这样做,它将在运行时为此创建一个对象;否则,它没有任何其他好处!

标签: scala generics extension-methods


【解决方案1】:

您需要将扩展​​方法纳入范围,即通过导入它们:

object Helpers {
  implicit class MapExt(val self: Map[String, Any]) extends AnyVal {
    // gets a map value for specified key casting as required type
    def getValueAs[A](key: String): A = self(key).asInstanceOf[A]
  }
}

import Helpers._  // !
Map("foo" -> 2, "bar" -> 3.45).getValueAs[Int]("foo")  // works

【讨论】:

  • 给定:lub( List( typeOf[Map[String, String]], typeOf[AnyVal] ) ) === Anyextends AnyVal 不是 docs 没有意义吗?
  • @KevinMeredith extend AnyVal 与对等类型 (Map) 无关。它只是意味着扩展方法是静态分派的,而不是创建MapExt 的实际实例(因此它应该更快一些)。这在 Scala 中称为 value-class
  • @KevinMeredith “根据文档”,文档中是否有特定的行具有误导性?生成的代码包括对简单合成 MapExt 方法的调用,这可能会令人困惑,但不会分配。 Int 结果也必须取消装箱。
猜你喜欢
  • 2011-03-08
  • 2017-01-31
  • 1970-01-01
  • 2012-05-12
  • 1970-01-01
  • 2019-03-02
  • 1970-01-01
  • 2019-05-01
  • 2015-06-25
相关资源
最近更新 更多