我有一个数据集,其中包含一些颜色和相关日期的计数。
+-----------+----------+-----+
| color| Date|count|
+-----------+----------+-----+
| red|2014-05-26| 5|
| red|2014-05-02| 1|
| red|2015-04-02| 1|
| red|2015-04-26| 1|
| red|2015-09-26| 2|
| blue|2014-05-26| 3|
| blue|2014-06-02| 1|
| brown|2014-07-31| 2|
| green|2014-08-01| 2|
+-----------+----------+-----+
我想要每种颜色的最大数量和相关日期。我在Java 8中使用Spark 2.0.2。
当我使用max函数时,它删除了日期列,当我将日期放入groupBy
时,它会给出与输入数据集相同的表格。
df.groupBy(color).max("count").show();
+-----------+----------+
|color |max(count)|
+-----------+----------+
| red| 5|
| blue| 3|
| brown| 2|
| green| 2|
+-----------+----------+
预期产出:
+-----------+----------+----------+
|color | date|max(count)|
+-----------+----------+----------+
| red|2014-05-26| 5|
| blue|2014-05-26| 3|
| brown|2014-07-31| 2|
| green|2014-08-01| 2|
+-----------+----------+----------+
答案 0 :(得分:1)
另一个答案部分正确,因为first
将返回date
上分组生成的群组color
的第一个元素。
在问题中,max(count)
始终位于该特定颜色的第一个位置,因此声明:
df.groupBy(color).agg(first("date").alias(date),max("count")).show();
返回正确的结果。
如果您的数据是这样的:
df.show
// red with highest count is at the bottom of the group
+-----+----------+-----+
|color| date|count|
+-----+----------+-----+
| red|2014-05-02| 1|
| red|2015-04-02| 1|
| red|2015-04-26| 1|
| red|2015-09-26| 2|
| red|2014-05-26| 5|
| blue|2014-05-26| 3|
| blue|2014-06-02| 1|
|brown|2014-07-31| 2|
|green|2014-08-01| 2|
+-----+----------+-----+
有问题的查询将返回组中与计数1对应的第一个日期:
df.groupBy($"color").agg( first($"date").as("date") , max("count").as("count") ).show
+-----+----------+-----+
|color| date|count|
+-----+----------+-----+
|brown|2014-07-31| 2|
|green|2014-08-01| 2|
| blue|2014-05-26| 3|
| red|2014-05-02| 5|
+-----+----------+-----+
或者,您可以在此处使用窗口函数:
import org.apache.spark.sql.expression.Window
val window = Window.partitionBy($"color").orderBy($"count".desc)
df.withColumn("rn", row_number over window).where($"rn" === 1 ).drop($"rn").show
+-----+----------+-----+
|color| date|count|
+-----+----------+-----+
|brown|2014-07-31| 2|
|green|2014-08-01| 2|
| blue|2014-05-26| 3|
| red|2014-05-26| 5|
+-----+----------+-----+
答案 1 :(得分:-1)
在这里,您需要具有最大值的相关列,以便您可以使用agg()
函数获取最大值,并使用first()
这些相关列。
df.groupBy(color).agg(first("date").alias(date),max("count")).show();
+-----------+----------+----------+
|color | date|max(count)|
+-----------+----------+----------+
| red|2014-05-26| 5|
| blue|2014-05-26| 3|
| brown|2014-07-31| 2|
| green|2014-08-01| 2|
+-----------+----------+----------+