所以我有一个类型的地图
Gui, Border, Style, 2B2D39, 474d65
当我通过Map[String, AnyRef]
打印此地图时,它会提供以下输出
println
现在,如您在地图上看到的,我想针对键Map(revision ->
Map(comment -> "string1",
contributor -> Map(id -> "int1", username -> "string2"),
format -> "string3",
id -> "int2",
minor -> None,
model -> "string4",
parentid -> "int3",
sha1 -> "string5",
text -> Map(_VALUE -> "VALUE-THAT-I-WANT-TO-GET",
space -> ""),
timestamp -> Timestamp,
title -> "string6"))
获取值。
我尝试以this答案中解释的方式从嵌套地图中获取信息,但是它不起作用可能是因为它的类型为_VALUE
在简单的字符串变量中获取它的最佳方法是什么?
很抱歉,如果地图的可读性不足,请接受更好的编辑方式。但是已将其完整张贴以清楚地了解问题所在。
答案 0 :(得分:4)
因此,假设您有一个产生此类代码的同事。当然,那个人因不称职而被解雇。 las,您一直无法使用它,直到可以将其重写为适当的Scala。
这是您可能要做的一件事。它会编译并显示警告,但似乎会产生所需的结果。
def extract(m :collection.Map[String,AnyRef], key :String) :Option[String] = {
if (m.isDefinedAt(key)) Some(m(key).toString)
else {
val res = m.values
.collect{case ma:Map[String,AnyRef] => extract(ma,key)}
.dropWhile(_.isEmpty)
if (res.isEmpty) None else res.head
}
}
extract(badMap, "_VALUE") //res0: Option[String] = Some(VALUE-THAT-I-WANT-TO-GET)
extract(badMap, "_XALUE") //res1: Option[String] = None
答案 1 :(得分:3)
您可以包装地图(别名anymap)以定义getAs [T]方法,该方法返回Option等。
import scala.reflect.ClassTag
val m: Map[String, AnyRef] = Map("a" -> Map("b" -> Map("c" -> "d")))
type AnyMap = Map[String, AnyRef]
implicit class AnyMapWrapper(m: AnyMap) {
def getAs[T](key: String)(implicit ev: ClassTag[T]): Option[T] = m(key) match {
case i: T => Some(i.asInstanceOf[T])
case _ => None
}
}
println {
m.getAs[AnyMap]("a").flatMap(_.getAs[AnyMap]("b")).map(_("c"))
}
println {
for {
a <- m.getAs[AnyMap]("a")
b <- a.getAs[AnyMap]("b")
} yield b("c")
}
答案 2 :(得分:0)
详细(但明确)的版本可能是:
yourMap.get("revision") collect {
case Some(otherMap: Map[String, AnyRef]) => otherMap.get("text")
} collect {
case Some(yetAnotherMap: Map[String, AnyRef]) => yetAnotherMap.get("_VALUE")
}