序列化Parcelable和Serializable的区别

Parcelable和Serializable有什么用,它们有什么差别?

Parcelable和Serializable都可以实现序列化,使对象可以变为二进制流在内存中传输数据。在Android中,只要实现二者之一就可以使用Intent和Binder来传递数据。实现了Parcelable接囗的类依赖于Parcel这个类来实现数据传递,它并不是一个一般化用途的序列化机制,主要用于IPC机制下的高性能传输。

差别
  1. 来源上

Parcelable是Android提供的序列化接口,Serializable是Java提供的序列化接口。因此Parcelable只能在Android中使用,而Serializable可以在任何使用Java语言的地方使用。

  1. 使用上

Parcelable使用起来比较麻烦,序列化过程需要实现Parcelable的writeToParcel(Parcel dest, int f1ags)方法和describeContents()方法。其中describeContents()方法直接返回0就可以了。为了反序列化,还需要提供一个非空的名为CREATOR的静态字段,该字段类型是实现了Parcelable.Creator接口的类,一般用一个匿名内部类实现就可以了。现在也有一些插件可以方便地实现Parcelable接口。

Serializable的使用就比较简单,直接实现Serializable接口即可,该接口没有任何方法。序列化机制依赖于一个long型的serialVersionUID,如果没有显式的指定,在序列化运行时会基于该类的结构自动计算出一个值。如果类的结构发生变化就会导致自动计算出的serialVersionUID不同。这就会导致一个问题,序列化之后类如果新增了一个字段,反序列过程就会失败。一般会报InvalidClassException这样的异常。
而如果显式的指定了serialversionUID,只要类的结构不发生重大变化,如字段类型发生变化等,仅仅添加或者删除字段等都可以反序列化成功。
注意:如果要把对象持久化到存储设备或者通过网络传输到其它设备,最好使用Serializable。

  1. 效率上

Serializable的序列化和反序列化都需要使用到IO操作;而Parcelable不需要IO操作,Parcelable的效率要高于Serializable,Android中推荐使用Parcelable。

自定义一个类让其实现Parcelable,大致流程是什么?

自定义一个类让其实现Parcelable接口,大致流程是先实现该接口的writeToParcel(Parcel dest, int flags)describeContents()方法。然后添加一个Parcelable.Creator类型的名字为CREATOR的非空字段。例如:

public class Person implements Parcelable {
    private String name;
    private int age;
    
    //...
    
    @Override
    public int describeContents() {
        return 0;
    }
    
    @Override
    public void writeToParcel(Parcel dest, int flags) {
        dest.writeString(name); // 写出name
        dest.writeInt(age); // 写出age
    }
    
    public static final Parcelable.Creator<Person> CREATOR = new Parcelable.
            Creator<Person>() {
            
        @Override
        public Person createFromParcel(Parcel source) {
            Person person = new Person();
            person.name = source.readString(); // 读取name
            person.age = source.readInt(); // 读取age
            return person;
        }
        
        @Override
        public Person[] newArray(int size) {
            return new Person[size];
        }
    };
}

该类中的字段类型除了基本类型和String及它们对应的数组,如果有其它自定义的类型,也需要实现Parcelable或者Serializable接口。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值