android.os.parcelable,Android中的Parcelable接口

Android中的android.os.Parcelable接口用于替代Java序列化Serializable接口,Fragment以及Activtity之间都需要传递数据,有时甚至包含结构非常复杂的对象,这就需要先将这个对象序列化成二进制流,然后再进行传递了。

比如Fragment1向Fragment2传递数据,下面是Fragment1中创建Fragment2并传送数据的方法:

在Fragment2中,直接得到这个Parcelable对象即可:

不过,既然Java已经有了Serializable,那还需要Parcelable干什么呢?而且Serializable接口使用起来也非常简洁。

原因有三个,第一是效率,第二是效率,第三还是效率:

Serializable用了很多反射,细心的人都知道,反射比正常的调用要慢100多倍

Serializable会创建很多临时对象,这些临时对象会导致很多次垃圾回收,影响效率

有细心的人士做过测试,基本上Parcelable要比Serializable快上10-20倍。下面这个图是比较结构

parcelable-vs-serializable.png

下面是android.os.Parcelable接口的定义,相比java.io.Serializable要复杂很多,不过,为了效率,你也只能忍了。

看起来你至少需要实现两个方法describeContents()和writeToParcel():

第一个方法返回数字,一般返回0就好,只有FileDescriptor有特殊,上面的常量有定义。至于这有什么用,我也没有找到相关的信息,如果有读者理解,请留言告知我。

第二个方法用于将对象写入到Parcel对象中。详见下面的例子。

接着自己来实现一个包含了姓和名两个String字段的对象,如下:

这里使用了Parcel.writeString()方法来将一个对象写入到序列化对象中,使用了Parcel.readString()从序列化对象中读取数据,一定要注意的是这里的写入和读取是有顺序的:先写的要先读。

注意,这里我们创建了一个私有的构造函数,这个构造函数的参数是Parcel对象,我们还创建了一个CREATOR的类变量,这个对象专门用于从序列化对象中创建ParcelableName对象,这是为了尽可能向外界隐藏序列化对象的实现细节,这种方式需要仔细琢磨,才能有所领悟。

值得提一下的是,Parcelable接口中还有一个ClassLoaderCreator接口,里面的createFromParcel()的第二个参数是一个ClassLoader对象,意味着我们可以反序列化不同的ClassLoader中的对象。

这种代码写起来的确是挺麻烦的,有一个开源项目通过Anotation+代码生成的方法可以简化定义Parcelable对象的过程:

看起来简单多了,不过话说回来,如果你需要序列化的对象比较小,而且次数不多,不影响效率,你还是可以继续使用Serializable接口的,毕竟编码和维护的代价都小得多。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值