如何使用列值爆炸



我一直在尝试获取org.apache.spark.sql.explode的动态版本,没有运气:我有一个带有日期列的数据集,称为event_date,另一个称为no_of_days_gap的列。我想使用no_of_days_gap使用explode函数来创建行的克隆。我的第一个尝试之一是使用此方法:

myDataset.withColumn("clone", explode(array((0 until col("no_of_days_gap")).map(lit): _*)))

但是,col("no_of_days_gap")Column型,并且预期Int。我还尝试了其他各种方法。那么我该如何工作呢?

P.S。:我设法获得了使用map功能的替代解决方案,然后调用flatMap,但是,我非常有兴趣了解如何使withColumn方法工作。

以下呢?

scala> val diddy = Seq(
     |   ("2017/03/07", 4),
     |   ("2016/12/09", 2)).toDF("event_date", "no_of_days_gap")
diddy: org.apache.spark.sql.DataFrame = [event_date: string, no_of_days_gap: int]
scala> diddy.flatMap(r => Seq.fill(r.getInt(1))(r.getString(0))).show
+----------+
|     value|
+----------+
|2017/03/07|
|2017/03/07|
|2017/03/07|
|2017/03/07|
|2016/12/09|
|2016/12/09|
+----------+
// use explode instead
scala> diddy.explode("no_of_days_gap", "events") { n: Int => 0 until n }.show
warning: there was one deprecation warning; re-run with -deprecation for details
+----------+--------------+------+
|event_date|no_of_days_gap|events|
+----------+--------------+------+
|2017/03/07|             4|     0|
|2017/03/07|             4|     1|
|2017/03/07|             4|     2|
|2017/03/07|             4|     3|
|2016/12/09|             2|     0|
|2016/12/09|             2|     1|
+----------+--------------+------+

但是,如果您坚持使用withColumn,那么...是……它!扣紧!

diddy
  .withColumn("concat", concat($"event_date", lit(",")))
  .withColumn("repeat", expr("repeat(concat, no_of_days_gap)"))
  .withColumn("split", split($"repeat", ","))
  .withColumn("explode", explode($"split"))

您必须使用UDF:

val range = udf((i: Integer) => (0 until i).toSeq)
df
  .withColumn("clone", range($"no_of_days_gap"))  // Add range
  .withColumn("clone", explode($"clone"))  // Explode

相关内容

  • 没有找到相关文章

最新更新