[Exception]java.io.StreamCorruptedException: invalid stream header

[Exception]java.io.StreamCorruptedException: invalid stream header

今天在做模型序列化保存的时候出现这个异常,首先给大家介绍一下场景。我在Spark-mllib的环境下将训练好的模型序列化,并且将序列化的Byte数组存入数据库。但是在从数据库中读取出Byte数组后,反序列化的过程中弹出这个异常。

异常定位的代码如下:

*** val reloadedModel: KMeansModel = reloadModel("kmeans")

def reloadModel(modelName: String): KMeansModel = {
    val utils: DMUtils = new DMUtils()
    val conn: Connection = utils.getConnection
    var sql = "select * from kmeansmodel3 where modelName='kmeans';"
    val pstmt: PreparedStatement = conn.prepareStatement(sql)
    var model: KMeansModel = null

    try {
        val set: ResultSet = pstmt.executeQuery()
        while (set.next()) {
            //val modelName: String = set.getString(1)
            val bytes: Array[Byte] = set.getBytes(3)
            bytes.foreach(print(_))
            *** model = bytesArray2Model(bytes)

        }
    } catch {
        case ex: Exception => {}
        println("select model operation fail ...")
        ex.printStackTrace()
    } finally {
        // 释放资源
        pstmt.close()
        conn.close()
    }
    model
}

def bytesArray2Model(bytesArray: Array[Byte]) = {

    var bais: ByteArrayInputStream = null
    var ois: ObjectInputStream = null
    var model: KMeansModel = null

    try {
        bais = new ByteArrayInputStream(bytesArray)
        *** ois = new ObjectInputStream(bais)
        model = ois.readObject().asInstanceOf[KMeansModel]
    } catch {
        case ex: Exception => {
            println("deserialize fail ...")
            ex.printStackTrace()
        }
    } finally {
        ois.close()
        bais.close()
    }
    model
}

出问题的语句我使用***来标注,可以看到最终定位在ois = new ObjectInputStream(bais),显然反序列化出了问题。

思路:首先,我搜索了大量scala序列化和反序列化的操作案例,发现我的操作与博客的做法并无太大区别,唯一的区别就是我经过了数据库的IO,所以可以考虑是数据库IO过程中出了问题。然后,我写了一个小案例来测试是否是因为模型的原因序列化出问题,但是结果是成功反序列化了,那么问题就可以定位在数据库。接下来,我将序列化前与反序列化后的Byte数组做了打印,发现结果不一致,那么一定就是IO出了问题。最后,我在所使用的数据库的程序员手册中找到了正确类型,修改表结构,成功通过反序列化。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值