我正在使用Spark SQL从表中提取行。其中一些数据反复出现,我正在尝试计算出现次数。本质上,我正在尝试执行基本的“字数统计”示例,但我的数据不是(Word : String, Count : Int)
形式,而是有一行数据替换字/字符串。
更具体地说,我的数据看起来像:RDD[((row), count)]
,其中row是从sql表中提取的,包含字符串,双精度,整数等。
它是RDD
形式,因为我想使用reduceByKey
。见:Avoid groupByKey。它是一个(Key, Value)
对,带有一个很长的密钥(来自sql数据库的某一行),它的值是“字数”。
我的应用正在执行此操作:
myDataframe
// Append a 1 to each row
.map(row => (row, 1))
// Convert to RDD so we can use the reduceByKey method
.rdd
// Add up the 1's corresponding to matching keys
.reduceByKey(_ + _)
//Filter by rows that show up more than 10 times
.filter(_._2 > 100)
...
现在假设我的行数据包含(string, double, int)
。
这是我想将数据从RDD[((string, double, int), count)]
解压缩到RDD[(string, double, int, count)]
的地方,这样我最终可以将这些数据保存到另一个SQL表中。
是否有一些方法允许我解压缩这个...嵌套元组的内容......有点像?
我的解决方案是“解压缩”RDD的元素,如下所示:
.map(row => (row._1._1, row._1._2, row._1._3, row._2))
但必须有更好的方法!如果我决定从行中获取更多元素,我必须修改此.map()
调用。
谢谢!
答案 0 :(得分:1)
您可以使用Row
的{{1}}和toSeq
,如下例所示:
fromSeq
答案 1 :(得分:1)
您不必恢复使用RDD;您正确引用的文章警告使用RDD.groupByKey
,但不应该应用于DataFrame的groupBy
。在DataFrame上使用groupBy
是安全的(并且高效)!查看更多here。
因此,要按所有的DataFrame列进行分组,请计算每个组的出现次数,并过滤计数为>的组。 10,你可以简单地使用:
df.groupBy(df.columns.map(col): _*) // alternatively: df.groupBy(df.columns.head, df.columns.tail: _*)
.count()
.filter($"count" > 10)
结果的架构类似于输入,附加count
长列。