我已经聚集了一些数据,我创建了一个RDD,其中包含元素的id和相应的簇,通过压缩包含元素的id的id_rdd
和包含该元素的cluster_rdd
每个id的适当簇号。
rdd: org.apache.spark.rdd.RDD[(String, String)]
我收到了一个新的数据点并预测了这个数据点所在的集群:
val location = model.predict(vector)
location: Int = 1
现在我希望得到rdd
的所有元素与向量属于同一个集群。我以为我可以使用过滤器:
val output = rdd.filter(_._2 == s"$location")
然而我收到错误:
org.apache.spark.SparkException: Task not serializable
at org.apache.spark.util.ClosureCleaner$.ensureSerializable(ClosureCleaner.scala:304)
at org.apache.spark.util.ClosureCleaner$.org$apache$spark$util$ClosureCleaner$$clean(ClosureCleaner.scala:294)
at org.apache.spark.util.ClosureCleaner$.clean(ClosureCleaner.scala:122)
at org.apache.spark.SparkContext.clean(SparkContext.scala:2055)
at org.apache.spark.rdd.RDD$$anonfun$filter$1.apply(RDD.scala:341)
at org.apache.spark.rdd.RDD$$anonfun$filter$1.apply(RDD.scala:340)
at org.apache.spark.rdd.RDDOperationScope$.withScope(RDDOperationScope.scala:150)
at org.apache.spark.rdd.RDDOperationScope$.withScope(RDDOperationScope.scala:111)
at org.apache.spark.rdd.RDD.withScope(RDD.scala:316)
at org.apache.spark.rdd.RDD.filter(RDD.scala:340)
.....
Caused by: java.io.NotSerializableException: org.apache.spark.mllib.clustering.KMeans
我该如何避免这种情况?我尝试了该命令的变体,但由于某种原因,它总是尝试序列化以前使用的(和完成的)聚类算法。我在运行过滤器之前尝试缓存rdd
但是我得到了同样的错误。为什么口译员会选择那个?这可能是由于spark的懒惰评估而刚刚为rdd
计算正确的聚类值?如果没有使用collect(我宁可避免使用)或者在RDD和Dataframe之间跳转,还有其他方法可以解决这个问题吗?