web-dev-qa-db-ja.com

spark dataframe left outer joinの後にnull値を0に置き換える

leftrightという2つのデータフレームがあります。

scala> left.printSchema
root
|-- user_uid: double (nullable = true)
|-- labelVal: double (nullable = true)
|-- probability_score: double (nullable = true)

scala> right.printSchema
root
|-- user_uid: double (nullable = false)
|-- real_labelVal: double (nullable = false)

次に、それらを結合して、結合されたデータフレームを取得します。 左外部結合です。 natjoin関数に興味のある人なら誰でもここで見つけることができます。

https://Gist.github.com/anonymous/f02bd79528ac75f57ae8

scala> val joinedData = natjoin(predictionDataFrame, labeledObservedDataFrame, "left_outer")

scala> joinedData.printSchema
|-- user_uid: double (nullable = true)
|-- labelVal: double (nullable = true)
|-- probability_score: double (nullable = true)
|-- real_labelVal: double (nullable = false)

これは左外部結合であるため、user_uidが右側に存在しない場合、real_labelVal列はnullになります。

scala> val realLabelVal = joinedData.select("real_labelval").distinct.collect
realLabelVal: Array[org.Apache.spark.sql.Row] = Array([0.0], [null])

realLabelVal列のnull値を1.0に置き換えたい

現在私は次のことをしています:

  1. Real_labelval列のインデックスを見つけ、spark.sql.Row APIを使用してnullを1.0に設定します。 (これによりRDD [Row]が得られます)
  2. 次に、結合されたデータフレームのスキーマを適用して、クリーンなデータフレームを取得します。

コードは次のとおりです。

 val real_labelval_index = 3
 def replaceNull(row: Row) = {
    val rowArray = row.toSeq.toArray
     rowArray(real_labelval_index) = 1.0
     Row.fromSeq(rowArray)
 }

 val cleanRowRDD = joinedData.map(row => if (row.isNullAt(real_labelval_index)) replaceNull(row) else row)
 val cleanJoined = sqlContext.createDataFrame(cleanRowRdd, joinedData.schema)

これを行うためのエレガントで効率的な方法はありますか?

グーグルはあまり役に立ちませんでした。前もって感謝します。

16
Mihir Shinde

naを使ってみましたか

joinedData.na.fill(1.0, Seq("real_labelval"))
26
Justin Pihony