2015-10-18 3 views
5

私はカラムがuser, address1, address2, address3, phone1, phone2というデータフレームを持っています。 私はこのデータフレームを変換したい - 私が使用してマッピングするために列を変換することができましたuser, address, phone where address = Map("address1" -> address1.value, "address2" -> address2.value, "address3" -> address3.value)Spark Dataframe scalaを使用して複数の異なる列をMap列に変換

val mapData = List("address1", "address2", "address3") 
df.map(_.getValuesMap[Any](mapData)) 

が、私は私のDFにこれを追加する方法がわからないです。

私はスパークとスケーラに新しいですし、実際にここでいくつかの助けを使用することができます。

答えて

6

スパーク> = 2.0

あなたはudfをスキップして、SQL関数(Pythonでcreate_mapmap使用することができます。

import org.apache.spark.sql.functions.map 

df.select(
    map(mapData.map(c => lit(c) :: col(c) :: Nil).flatten: _*).alias("a_map") 
) 

スパーク< 2.0

を私の知る限りではそれを行う直接的な方法はありません。

val dfWithStruct = df.withColumn("address", struct(mapData.map(col): _*)) 

最大の利点は、それが簡単に値を扱うことができるということです。

import org.apache.spark.sql.functions.{udf, array, lit, col} 

val df = sc.parallelize(Seq(
    (1L, "addr1", "addr2", "addr3") 
)).toDF("user", "address1", "address2", "address3") 

val asMap = udf((keys: Seq[String], values: Seq[String]) => 
    keys.zip(values).filter{ 
    case (k, null) => false 
    case _ => true 
    }.toMap) 

val keys = array(mapData.map(lit): _*) 
val values = array(mapData.map(col): _*) 

val dfWithMap = df.withColumn("address", asMap(keys, values)) 

UDFを必要としない別のオプションは、代わりにマップのフィールドを構造体へのです:あなたはこのようなUDFを使用することができますさまざまなタイプの

関連する問題