将Spark DataFrame数据划分为单独的文件

时间:2016-11-11 18:18:02

标签: scala apache-spark dataframe amazon-s3 qubole

我从s3文件输入以下DataFrame,需要将数据转换为以下所需的输出。我使用Spark版本1.5.1和Scala,但可以用Python改为Spark。欢迎任何建议。

DataFrame输入:

name    animal   data
john    mouse    aaaaa
bob     mouse    bbbbb
bob     mouse    ccccc
bob     dog      ddddd

期望的输出:

john/mouse/file.csv
bob/mouse/file.csv
bob/dog/file.csv

terminal$ cat bob/mouse/file.csv
bbbbb
ccccc

terminal$ cat bob/dog/file.csv
ddddd

这是我尝试的现有Spark Scala代码:

val sc = new SparkContext(new SparkConf())
val sqlc = new org.apache.spark.sql.SQLContext(sc)
val df = sqlc.read.json("raw.gz")
val cols = Seq("name", "animal")
df.groupBy(cols.head, cols.tail: _*).count().take(100).foreach(println)

当前输出:

[john,mouse,1]
[bob,mouse,2]
[bob,dog,1]

我现有代码的一些问题是groupBy返回一个GroupedData对象,我可能不想对该数据执行count / sum / agg函数。我正在寻找一种更好的技术来分组和输出数据。数据集非常大。

1 个答案:

答案 0 :(得分:5)

这可以使用partitionBy的{​​{1}}选项来实现。一般语法如下:

DataFrameWriter

不幸的是,支持Spark 1.5中分区的唯一纯文本格式是JSON。

如果您可以将Spark安装更新为:

  • 1.6 - 您可以df.write.partitionBy("name", "animal").format(...).save(...) 格式使用partitionBy。如果您需要组(text)的单个输出文件,则还需要1.6。
  • 2.0 - 您可以repartition使用partitionBy格式。

我相信在1.5中你最好的选择是将文件写为JSON并转换单个输出文件。

如果不同csv的数量很小,您可以尝试为每个组执行单独的写入:

name', 'animals

但是当组合数量增加时,这不会扩展。