【问题标题】:Spark Task not serializable (Case Classes)Spark 任务不可序列化(案例类)
【发布时间】:2015-08-10 03:14:14
【问题描述】:

当我使用在闭包内扩展 Serializable 的案例类或类/对象时,Spark 会抛出 Task not serializable。

object WriteToHbase extends Serializable {
    def main(args: Array[String]) {
        val csvRows: RDD[Array[String] = ...
        val dateFormatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss")
        val usersRDD = csvRows.map(row => {
            new UserTable(row(0), row(1), row(2), row(9), row(10), row(11))
        })
        processUsers(sc: SparkContext, usersRDD, dateFormatter)
    })
}

def processUsers(sc: SparkContext, usersRDD: RDD[UserTable], dateFormatter: DateTimeFormatter): Unit = {

    usersRDD.foreachPartition(part => {

        val conf = HBaseConfiguration.create()
        val table = new HTable(conf, tablename)

        part.foreach(userRow => {
            val id = userRow.id
            val date1 = dateFormatter.parseDateTime(userRow.date1)
        })
        table.flushCommits()
        table.close()
    })
}

我的第一次尝试是使用案例类:

case class UserTable(id: String, name: String, address: String, ...) extends Serializable

我的第二次尝试是使用类而不是案例类:

class UserTable (val id: String, val name: String, val addtess: String, ...) extends Serializable {
}

我的第三次尝试是在类中使用伴生对象:

object UserTable extends Serializable {
    def apply(id: String, name: String, address: String, ...) = new UserTable(id, name, address, ...)
}

【问题讨论】:

  • 你能发布堆栈跟踪吗?
  • 从我在文档中看到的 HTable 是不可序列化的。

标签: scala hadoop serialization apache-spark closures


【解决方案1】:

它是 dateFormatter,我将它放在分区循环中,它现在可以工作了。

usersRDD.foreachPartition(part => {
    val id = userRow.id
    val dateFormatter = DateTimeFormat.forPattern("yyyy-MM-dd HH:mm:ss")
    val date1 = dateFormatter.parseDateTime(userRow.date1)
})

【讨论】:

【解决方案2】:

很可能函数“doSomething”是在你的类上定义的,它是不可序列化的。而是将“doSomething”函数移动到伴随对象(例如,使其成为静态)。

【讨论】:

  • 嗨 Holden,“doSomething”方法位于扩展 Serializable 的同一个类中。
  • @sophie 你能试着把它放在一个campanion对象里吗?即使 doSomething 所在的类被标记为可序列化,如果它的任何字段不是 Spark 的闭包清理器,也会尝试获取完整的东西。
  • 对不起,我使用的是一个对象,而不是一个类,并且主要方法在那里。我应该创建一个类并使我的对象成为伴随对象吗?
  • 我的意思是,如果它在一个对象中,它不应该捕获任何额外的位,所以我想我需要查看代码来说明它可能在哪里获取不可序列化的引用。
  • 嗨,Holden,我认为案例类是罪魁祸首。但我不知道如何使其可序列化
猜你喜欢
  • 2018-04-06
  • 2021-03-16
  • 1970-01-01
  • 2015-12-16
  • 2017-03-21
  • 2016-12-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多