我并不是说这一切都是优雅的,但它的工作原理。我明确而非隐含地使用来自JavaConversions
的转换来允许类型推断稍微有所帮助。在Scala 2.8中新增了JavaConversions
。
import collection.JavaConversions._
import java.util.{ArrayList, HashMap}
import collection.mutable.Buffer
val javaMutable = new HashMap[String, ArrayList[ArrayList[Double]]]
val scalaMutable: collection.Map[String, Buffer[Buffer[Double]]] =
asMap(javaMutable).mapValues(asBuffer(_).map(asBuffer(_)))
val scalaImmutable: Map[String, List[List[Double]]] =
Map(asMap(javaMutable).mapValues(asBuffer(_).map(asBuffer(_).toList).toList).toSeq: _*)
UPDATE:下面是一个使用implicits一组给定的转换应用到任意嵌套结构的另一种方法。
trait ==>>[A, B] extends (A => B) {
def apply(a: A): B
}
object ==>> {
def convert[A, B](a: A)(implicit a2b: A ==>> B): B = a
// the default identity conversion
implicit def Identity_==>>[A] = new (A ==>> A) {
def apply(a: A) = a
}
// import whichever conversions you like from here:
object Conversions {
import java.util.{ArrayList, HashMap}
import collection.mutable.Buffer
import collection.JavaConversions._
implicit def ArrayListToBuffer[T, U](implicit t2u: T ==>> U) = new (ArrayList[T] ==>> Buffer[U]) {
def apply(a: ArrayList[T]) = asBuffer(a).map(t2u)
}
implicit def HashMapToMap[K, V, VV](implicit v2vv: V ==>> VV) = new (HashMap[K, V] ==>> collection.Map[K, VV]) {
def apply(a: java.util.HashMap[K, V]) = asMap(a).mapValues(v2vv)
}
}
}
object test {
def main(args: Array[String]) {
import java.util.{ArrayList, HashMap}
import collection.mutable.Buffer
// some java collections with different nesting
val javaMutable1 = new HashMap[String, ArrayList[ArrayList[Double]]]
val javaMutable2 = new HashMap[String, ArrayList[HashMap[String, ArrayList[ArrayList[Double]]]]]
import ==>>.{convert, Conversions}
// here comes the elegant part!
import Conversions.{HashMapToMap, ArrayListToBuffer}
val scala1 = convert(javaMutable1)
val scala2 = convert(javaMutable2)
// check the types to show that the conversion worked.
scala1: collection.Map[String, Buffer[Buffer[Double]]]
scala2: collection.Map[String, Buffer[collection.Map[String, Buffer[Buffer[Double]]]]]
}
}
这不是更多的设计问题吗?这种结构的语义是什么?你为什么要转换对象? – 2010-02-13 13:38:49
其实我正在通过杰克逊json库从json文件读取这些数据(我试过sjson和lift-json都失败了)。杰克逊json没有scala API,所以我使用java API来完成这项工作。 – 2010-02-13 22:08:12