【发布时间】:2014-08-13 21:05:39
【问题描述】:
我需要生成一个可扩展的记录,给定一个 HList 的键和一个值映射,这是我想要实现的 MWE(您可以将它复制/粘贴到任何具有无形 2.0 的 REPL 中,在为了重现问题)
import shapeless._; import syntax.singleton._; import record._
case class Foo[T](column: Symbol)
val cols = Foo[String]('column1) :: HNil
val values = Map("column1" -> "value1")
object toRecord extends Poly1 {
implicit def Foo[T] = at[Foo[T]] { foo =>
val k = foo.column.name
val v = values.get(k)
(k ->> v)
}
}
val r = cols.map(toRecord)
// r: shapeless.::[Option[String] with shapeless.record.KeyTag[k.type,Option[String]] forSome { val k: String },shapeless.HNil] = Some(value1) :: HNil
val value = r("column1")
// error: No field String("column1") in record shapeless.::[Option[String] with shapeless.record.KeyTag[k.type,Option[String]] forSome { val k: String },shapeless.HNil]
val value = r("column1")
如果我尝试手动定义记录,一切都会按预期工作
val q = ("column1" ->> Some("value1")) :: HNil
// q: shapeless.::[Some[String] with shapeless.record.KeyTag[String("column1"),Some[String]],shapeless.HNil] = Some(value1) :: HNil
q("column1")
// Some[String] = Some(value1)
显然不同的是,在一种情况下,KeyTag 具有类型
KeyTag[String("column1"), Some[String]]
和在(非工作)其他
KeyTag[k.type,Option[String]] forSome { val k: String }
我感觉问题在于字符串k 不是静态已知的,但我不知道如何解决这个问题。
一般来说,有没有办法从键列表中动态生成可扩展记录?
我担心答案是使用宏,但如果存在其他解决方案,我会很高兴。
【问题讨论】: