【问题标题】:Map individual values in one dataframe with values in another dataframe将一个数据框中的单个值与另一个数据框中的值映射
【发布时间】:2018-10-09 19:27:59
【问题描述】:

我有一个包含两列的数据框 (DF1)

+--------+------+ |单词 |价值 | +--------+------+ |ABC |1.0 | |XYZ |2.0 | |DEF |3.0 | |GHI |4.0 | +--------+------+

和另一个像这样的数据帧(DF2)

+------------------------------+ |字符串 | +------------------------------+ |ABC DEF GHI | |XYZ ABC 定义 | +------------------------------+

我必须将 DF2 中的单个字符串值替换为它们在 DF1 中的对应值。例如,在操作之后,我应该取回这个数据帧。

+------------------------------+ |stringToDouble | +------------------------------+ |1.0 3.0 4.0 | |2.0 1.0 3.0 | +------------------------------+

我尝试了多种方法,但似乎无法找到解决方案。

 def createCorpus(conversationCorpus: Dataset[Row], dataDictionary: Dataset[Row]): Unit = {
 import spark.implicits._

 def getIndex(word: String): Double = {
 val idxRow = dataDictionary.selectExpr("index").where('words.like(word))
 val idx = idxRow.toString
 if (!idx.isEmpty) idx.trim.toDouble else 1.0
 }

 conversationCorpus.map { //eclipse doesnt like this map here.. throws an error..
    r =>
    def row = {
       val arr = r.getString(0).toLowerCase.split(" ")
       val arrList = ArrayBuffer[Double]()
       arr.map {
          str =>
          val index = getIndex(str)
       }
       Row.fromSeq(arrList.toSeq)
       }
       row

   }
 }

【问题讨论】:

    标签: scala apache-spark dataframe spark-dataframe


    【解决方案1】:

    组合多个数据框以创建新列需要连接。通过查看您的两个数据框,似乎我们可以通过df1words 列和df2string 列加入,但string 列需要explode 和稍后的组合(这可以通过在爆炸前为每一行提供唯一的 ID 来完成)。 monotically_increasing_id df2 中的每一行提供唯一的IDsplit 函数将 string 列转换为数组以进行爆炸。然后你可以join他们。然后剩下的步骤是通过groupBy聚合将分解的行组合回原始行

    最后可以使用udf函数将收集到的数组列更改为所需的字符串列

    长话短说,以下解决方案应该适合您

    import org.apache.spark.sql.functions._
    def arrayToString = udf((array: Seq[Double])=> array.mkString(" "))
    
    df2.withColumn("rowId", monotonically_increasing_id())
      .withColumn("string", explode(split(col("string"), " ")))
      .join(df1, col("string") === col("words"))
      .groupBy("rowId")
      .agg(collect_list("value").as("stringToDouble"))
      .select(arrayToString(col("stringToDouble")).as("stringToDouble"))
    

    这应该给你

    +--------------+
    |stringToDouble|
    +--------------+
    |1.0 3.0 4.0   |
    |2.0 1.0 3.0   |
    +--------------+
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-08-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-01-12
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多