函数结果的 Scala 类型转换
Scala type casting of function result
我是 scala 的新手,无法解决这个类型相关的问题。
尝试构建一个函数,该函数将键值元组列表(键可能不唯一)转换为属于使用 [=33 的额外列表选择的特定键的聚合值元组列表=]. out 需要有 Array[Array[Any]]:
的签名
示例:
输入:
[("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1)]
列:
COLUMNS = ["k1", "k2"]
输出:
[[10, 18, 13], [15, 1]]
我的尝试看起来像:
val COLUMNS = Array("k1", "k2")
def convert(result: Array[Tuple2[String, Any]]): Array[Array[Any]] = {
val grouped = result.groupBy(cell => cell._1)
val columns = grouped.mapValues(cell => cell.map(column => column._2))
val tuples = COLUMNS.map(col => columns.getOrElse(col, Array()))
return tuples
}
不过我收到以下错误:
<console>:21: error: type mismatch;
found : scala.collection.mutable.ArraySeq[Array[_]]
required: Array[Array[Any]]
return tuples
有人可以帮忙吗?注意我最后需要 Array[Array[Any]] 类型......
谢谢。
你应该只为空数组明确指定Any
,因为它在这里默认有Nothing
类型(我也删除了不必要的return和非常规的大写锁定,简化的lambdas) :
val Columns = Array("k1", "k2")
def convert(result: Array[(String, Any)]): Array[Array[Any]] = {
val grouped = result.groupBy(_._1)
val columns = grouped.mapValues(_.map(_._2))
Columns.map(columns.getOrElse(_, Array[Any]()))
}
scala> convert(Array(("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1)))
res2: Array[Array[Any]] = Array(Array(10, 18, 13), Array(15, 1))
groupBy
是这类作品的关键:
val kvs = Array(("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1))
scala> Array("k1", "k2") map kvs.groupBy(_._1) map (_ map (_._2))
res16: Array[Array[Int]] = Array(Array(10, 18, 13), Array(15, 1))
请注意,我们正在利用 Map
可以用作从键到值的 函数 这一事实。在这种情况下 groupBy
的结果是从键到包含它的元组的 Map
;我们 map
Map
(将其用作函数)在感兴趣的键上获取它们的元组,然后从中提取值。
如果您需要的某些键可能根本不存在于输入中,您可以使用 withDefaultValue
表示在这种情况下应返回一个空数组:
scala> Array("k1", "k2", "k9") map (kvs.groupBy(_._1) withDefaultValue Array()) map (_ map (_._2))
res17: Array[Array[Int]] = Array(Array(10, 18, 13), Array(15, 1), Array())
生成的类型将尽可能具体,这可能正是您想要的。但是当然,如果你想扩大它,你可以使用类型归属来实现,或者简单地通过使用更宽的类型声明接收结果的变量。
我是 scala 的新手,无法解决这个类型相关的问题。
尝试构建一个函数,该函数将键值元组列表(键可能不唯一)转换为属于使用 [=33 的额外列表选择的特定键的聚合值元组列表=]. out 需要有 Array[Array[Any]]:
的签名示例:
输入:
[("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1)]
列:
COLUMNS = ["k1", "k2"]
输出:
[[10, 18, 13], [15, 1]]
我的尝试看起来像:
val COLUMNS = Array("k1", "k2")
def convert(result: Array[Tuple2[String, Any]]): Array[Array[Any]] = {
val grouped = result.groupBy(cell => cell._1)
val columns = grouped.mapValues(cell => cell.map(column => column._2))
val tuples = COLUMNS.map(col => columns.getOrElse(col, Array()))
return tuples
}
不过我收到以下错误:
<console>:21: error: type mismatch;
found : scala.collection.mutable.ArraySeq[Array[_]]
required: Array[Array[Any]]
return tuples
有人可以帮忙吗?注意我最后需要 Array[Array[Any]] 类型...... 谢谢。
你应该只为空数组明确指定Any
,因为它在这里默认有Nothing
类型(我也删除了不必要的return和非常规的大写锁定,简化的lambdas) :
val Columns = Array("k1", "k2")
def convert(result: Array[(String, Any)]): Array[Array[Any]] = {
val grouped = result.groupBy(_._1)
val columns = grouped.mapValues(_.map(_._2))
Columns.map(columns.getOrElse(_, Array[Any]()))
}
scala> convert(Array(("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1)))
res2: Array[Array[Any]] = Array(Array(10, 18, 13), Array(15, 1))
groupBy
是这类作品的关键:
val kvs = Array(("k1", 10), ("k2", 15), ("k1", 18), ("k3", 23), ("k1", 13), ("k2", 1))
scala> Array("k1", "k2") map kvs.groupBy(_._1) map (_ map (_._2))
res16: Array[Array[Int]] = Array(Array(10, 18, 13), Array(15, 1))
请注意,我们正在利用 Map
可以用作从键到值的 函数 这一事实。在这种情况下 groupBy
的结果是从键到包含它的元组的 Map
;我们 map
Map
(将其用作函数)在感兴趣的键上获取它们的元组,然后从中提取值。
如果您需要的某些键可能根本不存在于输入中,您可以使用 withDefaultValue
表示在这种情况下应返回一个空数组:
scala> Array("k1", "k2", "k9") map (kvs.groupBy(_._1) withDefaultValue Array()) map (_ map (_._2))
res17: Array[Array[Int]] = Array(Array(10, 18, 13), Array(15, 1), Array())
生成的类型将尽可能具体,这可能正是您想要的。但是当然,如果你想扩大它,你可以使用类型归属来实现,或者简单地通过使用更宽的类型声明接收结果的变量。