安卓传值中使用Serializable和Parcelable的区别
在安卓开发中,我们经常会遇到这样一个问题,就是要在两个Activity之间传递一个实体对象,那么我们就会用到Serializable或者 Parcelable,这两个方法是用来序列化数据的,主要是用在不同的Activity之间在通过intent进行通信的时候,数据传输时,Data部 分的传输。
我们一般的在两个Activity之间传递参数是这样的,如下:
Intent it=new Intent();
Bundle bd=new Bundle();
bd.putInt("aa",20);
bd.putString("bb",ok);
it.setExtras(bd);
it.setClass(Activity1.this.class,Activity2.this.class)
startActivity(it,Activity2.this.class);
就这样传递,然后在第二个Activity中接收,如下:
Bundle bd1=(Bundle)getIntent().getExtras();
String str=bd1.getString("bb");
int ii=bd1.getInt("aa");
这样,就得到了传递的数据,如果只是传递一些普通的数据,这个方法就可以了,但是如果传输的是一个自定义的结构(例如 自定义的类),或是嵌套(结构) 数据,就要进行序列化了,否则就会乱码无法解析了。比如说,自定义一个类:
public Book {
private string bookname;
private string author;
Book(string s1,string s2){bookname=s1;author=s2}
public Setbookname(string s){bookname=s;}
public Setauthor(string s){author=s;}
public string getbookname(){return bookname ; }
public string getauthor(){return author;}
}
如果要传递这个类,那么就要用到Serializable或者Parcelable了。
序列化原因:
1.永久性保存对象,保存对象的字节序列到本地文件中;
2.通过序列化对象在网络中传递对象;
3.通过序列化在进程间传递对象。
但是Serializable与Parcelable两个都是序列化,什么时候用哪个呢?
1.在使用内存的时候,Parcelable 类比Serializable性能高,所以推荐使用Parcelable类。
2.Serializable在序列化的时候会产生大量的临时变量,从而引起频繁的GC。
3.Parcelable不能使用在要将数据存储在磁盘上的情况,因为Parcelable不能很好的保证数据的持续性在外界有变化的情况下。尽管Serializable效率低点, 也不提倡用,但在这种情况下,还是建议你用Serializable 。
实现的时候
1.Serializable 的实现,只需要 implements Serializable 即可。这只是给对象打了一个标记,系统会自动将其序列化。
比如说,像下面这样:
public class Person implements Serializable{ private String name; private int age; public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Person [name=" + name + ", age=" + age + "]"; } }
发数据与收数据如下:
Intent intent=new Intent(MainActivity.this,MainActivity2.class); Person person=new Person("张三", 10); intent.putExtra("键", person); startActivity(intent); Person person= (Person) getIntent().getSerializableExtra("键");//在另一个活动中接收数据
2.Parcelabel 的实现,需要在类中添加一个静态成员变量 CREATOR,这个变量需要继承 Parcelable.Creator 接口。
以数据类为Person为例:
public class Person implements Parcelable{ private String name; private int age; public Person(){ } public Person(String name, int age) { super(); this.name = name; this.age = age; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Person [name=" + name + ", age=" + age + "]"; } //必须重写的两个方法 @Override public int describeContents() {//第一步:返回0 return 0; } @Override//第二步:写出成员变量 public void writeToParcel(Parcel dest, int flags) { dest.writeString(name);//写出name dest.writeInt(age);//写出age } //第三步:必须创建一个CREATOR的常量,接着重写它的两个方法 (名字必须为CREATOR) 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]; } }; }
intent发送与接收数据
发送数据:intent.putExtra(String name, Parcelable value);
Person person= (Person) getIntent().getParcelableExtra("键");//接收数据
对比一下:
Serializable的方式较为简单,但由于会把整个对象进行序列化,因此效率方面会比 Parcelable 方式低一
些,所以在通常情况下还是更加推荐使用 Parcelable 的方式来实现 Intent 传递对象的功能