我有dataFrame
如下所示,想要使用Scala添加备注
id val visits
111 2 1
111 2 1
112 4 2
112 5 4
113 6 1
预期输出应低于
id val visits remarks
111 2 1 Ramdom
111 2 1 Ramdom
112 4 2 Less visit
112 5 4 More visit
113 6 1 One visit
备注应为:
Id的 Ramdom 有两条具有相同价值的记录。访问
Id的一次访问只有一条包含任何访问次数的记录
ID的减少访问次数有两条记录,与其他记录相比,访问量较少
对于ID,更多访问有多条记录具有不同的价值和访问次数。
答案 0 :(得分:2)
可能不是最好的解决方案,但它是一个有效的解决方案:
首先按dataFrame
和val
对您的visits
进行分组及其计数
val grouped = df.groupBy("id").agg(max($"val").as("maxVal"), max($"visits").as("maxVisits"), min($"val").as("minVal"), min($"visits").as("minVisits"), count($"id").as("count"))
然后定义实现逻辑的UDF
:
val remarks = functions.udf ((value: Int, visits: Int, maxValue: Int, maxVisits: Int, minValue: Int, minVisits: Int, count: Int) =>
if (count == 1) {
"One Visit"
}else if (value == maxValue && value == minValue && visits == maxVisits && visits == minVisits) {
"Random"
}else {
if (visits < maxVisits) {
"Less Visits"
}else {
"More Visits"
}
}
)
然后通过dataFrame
加入原始id
和已分组的一个,并使用UDF
添加所需的列。最后从输出中删除不需要的列:
df.join(grouped, Seq("id"))
.withColumn("remarks", remarks($"val", $"visits", $"maxVal", $"maxVisits", $"minVal", $"minVisits", $"count"))
.drop("maxVal","maxVisits", "minVal", "minVisits", "count")
输出:
+---+----+-------+-----------+
| id| val| visits| remarks|
+---+----+-------+-----------+
|112| 4| 2|Less Visits|
|112| 5| 4|More Visits|
|113| 6| 1| One Visit|
|111| 2| 1| Random|
|111| 2| 1| Random|
+---+----+-------+-----------+
P.S。记得导入功能
import org.apache.spark.sql.functions