2017-09-19 82 views
0

這是輸入火花數據幀。基於「典型」我需要這個數據幀分成多個子dataframes,如下Spark生成來自超級數據幀優化方法的子數據幀

val dsTotal = fr.toDF("Key","Code") 
dsTotal.show() 

-------------- 
|key | Code | 
-------------- 
|200 | DS | 
|300 | CP | 
|400 | DS | 
|76 | OR | 
|45 | CP | 
|34 | DS | 
|33 | OR | 
|200 | DS | 
-------------- 

我已經使用過濾器選項反覆在同一個超級數據幀創建子dataframes。是否有其他更好的方法來產生子dataframes

val ds1 = dsTotal.filter(col("Code").equalTo("CP")) 
ds1.show() 
-------------- 
|key | Code | 
-------------- 
|45 | CP | 
|300 | CP | 
-------------- 

val ds2 = dsTotal.filter(col("Code").equalTo("DS")) 
ds2.show() 
-------------- 
|key | Code | 
-------------- 
|200 | DS | 
|400 | DS | 
|200 | DS | 
|34 | DS | 
-------------- 

val ds3 = dsTotal.filter(col("Code").equalTo("OR")) 
ds3.show() 
-------------- 
|key | Code | 
-------------- 
|76 | OR | 
|33 | OR | 
-------------- 
+0

接下來你打算怎樣處理你的數據框?如果您只需要保存,請在DataFrameWriter上使用'partitionBy'。有關詳細信息,請參閱https://stackoverflow.com/questions/42645836/split-dataset-based-on-column-values-in-spark。 –

+0

我只是想分割一個數據幀到子數據框中,以便我可以在後續編碼中使用這些子數據框。 – raam

回答

1

filterselect是我所見過的split一個dataframesubdataframe是最好的方法之一。

所以你有最好的辦法之一,但你的filter有靜態檢查Code,這可以通過以下操作來避免。

第一步是獲得Code列的distinct

import org.apache.spark.sql.functions._ 
val array = df.select(collect_list("Code")).first()(0).asInstanceOf[mutable.WrappedArray[String]].distinct 

這應該給你

WrappedArray(DS, CP, OR) 

下一步將遍歷distinct值和subdataframe 4S店在hashmap

val splittedDFs : mutable.HashMap[String, DataFrame] = mutable.HashMap.empty[String, DataFrame] 
for(key <- array){ 
    splittedDFs ++= mutable.HashMap(key -> df.filter($"Code" === key)) 
} 

現在你可以訪問子非數據幀

splittedDFs("CP").show(false) 

這應該是

+---+----+ 
|key|Code| 
+---+----+ 
|300|CP | 
|45 |CP | 
+---+----+ 

可以使用select代替filter了。

我希望答案有幫助