我正在尝试在普通的 Scala 而不是 Spark 中寻找爆炸函数或其等效函数。使用 Spark 中的爆炸功能,我能够将具有多个元素的一行平展为多行,如下所示。
scala> import org.apache.spark.sql.functions.explode
import org.apache.spark.sql.functions.explode
scala> val test = spark.read.json(spark.sparkContext.parallelize(Seq("""{"a":1,"b":[2,3]}""")))
scala> test.schema
res1: org.apache.spark.sql.types.StructType = StructType(StructField(a,LongType,true), StructField(b,ArrayType(LongType,true),true))
scala> test.show
+---+------+
| a| b|
+---+------+
| 1|[2, 3]|
+---+------+
scala> val flat = test.withColumn("b",explode($"b"))
flat: org.apache.spark.sql.DataFrame = [a: bigint, b: bigint]
scala> flat.show
+---+---+
| a| b|
+---+---+
| 1| 2|
| 1| 3|
+---+---+
Run Code Online (Sandbox Code Playgroud)
在不使用 Spark 的情况下,普通 scala 中是否有爆炸等效函数?如果 Scala 中没有可用的爆炸功能,我是否可以实现它?
flatMap在这种情况下,简单应该可以帮助您。我不知道您想在 Scala 中使用的确切数据结构,但让我们举一个有点人为的例子:
val l: List[(Int, List[Int])] = List(1 -> List(2, 3))
val result: List[(Int, Int)] = l.flatMap {
case (a, b) => b.map(i => a -> i)
}
println(result)
Run Code Online (Sandbox Code Playgroud)
这将产生下一个结果:
List((1,2), (1,3))
Run Code Online (Sandbox Code Playgroud)
更新
正如@jwvh 在评论部分所建议的那样,或者使用for-comprehension构造和隐藏显式flatMap&map调用可以获得相同的结果:
val result2: List[(Int, Int)] = for((a, bList) <- l; b <- bList) yield a -> b
Run Code Online (Sandbox Code Playgroud)
希望这可以帮助!
| 归档时间: |
|
| 查看次数: |
166 次 |
| 最近记录: |