public class Person implements Serializable{ private static final long serialVersionUID = -7060210544600464481L; private String name; private int 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; }}2).Implements Parcelable 接口(不仅仅需要声明,还需要实现内部的相应方法)public class Book implements Parcelable{ private String bookName; private String author; private int publishDate;public Book(){ }public String getBookName(){return bookName; }public void setBookName(String bookName){this.bookName = bookName; }public String getAuthor(){return author; }public void setAuthor(String author){this.author = author; }public int getPublishDate(){return publishDate; }public void setPublishDate(int publishDate){this.publishDate = publishDate; }@Override public int describeContents(){return 0; }@Override public void writeToParcel(Parcel out, int flags){out.writeString(bookName);out.writeString(author);out.writeInt(publishDate); }public static final Parcelable.Creator<Book> CREATOR = new Creator<Book>(){ @Overridepublic Book[] newArray(int size){ return new Book[size];}@Overridepublic Book createFromParcel(Parcel in){ return new Book(in);} };public Book(Parcel in){//如果元素数据是list类型的时候需要: lits = new ArrayList<?> in.readList(list); 否则会出现空指针异常.并且读出和写入的数据类型必须相同.如果不想对部分关键字进行序列化,可以使用transient关键字来修饰以及static修饰.bookName = in.readString();author = in.readString();publishDate = in.readInt(); }} 我们知道在Java应用程序当中对类进行序列化操作只需要实现Serializable接口就可以,由系统来完成序列化和反序列化操作,但是在Android中序列化操作有另外一种方式来完成,那就是实现Parcelable接口.也是Android中特有的接口来实现类的序列化操作.原因是Parcelable的性能要强于Serializable.因此在绝大多数的情况下,Android还是推荐使用Parcelable来完成对类的序列化操作的. 
性能差异:
Nexus 10
Serializable: 1.0004ms, Parcelable: 0.0850ms – 提升10.16倍。
Nexus 4
Serializable: 1.8539ms – Parcelable: 0.1824ms – 提升11.80倍。
Desire Z
Serializable: 5.1224ms – Parcelable: 0.2938ms – 提升17.36倍。
由此可以得出: Parcelable 比 Serializable快了10多倍。
从相对的比较我们可以看出,Parcelable的性能要比Serializable要优秀的多,因此在Android中进行序列化操作的时候,我们需要尽可能的选择前者,需要花上大量的时间去实现Parcelable接口中的内部方法.
4.Android中如何使用Parcelable进行序列化操作
说了这么多,我们还是来看看Android中如何去使用Parcelable实现类的序列化操作吧.
Implements Parcelable的时候需要实现内部的方法:
1).writeToParcel 将对象数据序列化成一个Parcel对象(序列化之后成为Parcel对象.以便Parcel容器取出数据)
2).重写describeContents方法,默认值为0
3).Public static final Parcelable.Creator<T>CREATOR (将Parcel容器中的数据转换成对象数据) 同时需要实现两个方法:
3.1 CreateFromParcel(从Parcel容器中取出数据并进行转换.)
3.2 newArray(int size)返回对象数据的大小
因此,很明显实现Parcelable并不容易。实现Parcelable接口需要写大量的模板代码,这使得对象代码变得难以阅读和维护。具体的实例就是上面Parcelable的实例代码.就不进行列举了.(有兴趣的可以去看看Android中NetWorkInfo的源代码,是关于网络连接额外信息的一个相关类,内部就实现了序列化操作.大家可以去看看)
5.Parcelable的工作原理
无论是对数据的读还是写都需要使用Parcel作为中间层将数据进行传递.Parcel涉及到的东西就是与C++底层有关了.都是使用JNI.在Java应用层是先创建Parcel(Java)对象,然后再调用相关的读写操作的时候.就拿读写32为Int数据来说吧:
static jint android_os_Parcel_readInt(JNIEnv* env, jobject clazz){ Parcel* parcel = parcelForJavaObject(env, clazz); if (parcel != NULL) {return parcel->readInt32(); } return 0;}调用的方法就是这个过程,首先是将Parcel(Java)对象转换成Parcel(C++)对象,然后被封装在Parcel中的相关数据由C++底层来完成数据的序列化操作.status_t Parcel::writeInt32(int32_t val){ return writeAligned(val);} template<class t="">status_t Parcel::writeAligned(T val) { COMPILE_TIME_ASSERT_FUNCTION_SCOPE(PAD_SIZE(sizeof(T)) == sizeof(T));if ((mDataPos+sizeof(val)) <= mDataCapacity) {restart_write:*reinterpret_cast<t*>(mData+mDataPos) = val;return finishWrite(sizeof(val)); }status_t err = growData(sizeof(val)); if (err == NO_ERROR) goto restart_write; return err;}真正的读写过程是由下面的源代码来完成的.status_t Parcel::continueWrite(size_t desired){ // If shrinking, first adjust for any objects that appear // after the new data size. size_t objectsSize = mObjectsSize; if (desired < mDataSize) {if (desired == 0) { objectsSize = 0;} else { while (objectsSize > 0) {if (mObjects[objectsSize-1] < desired) break;objectsSize--; }} }if (mOwner) {// If the size is going to zero, just release the owner"s data.if (desired == 0) { freeData(); return NO_ERROR;}// If there is a different owner, we need to take// posession.uint8_t* data = (uint8_t*)malloc(desired);if (!data) { mError = NO_MEMORY; return NO_MEMORY;}size_t* objects = NULL;if (objectsSize) { objects = (size_t*)malloc(objectsSize*sizeof(size_t)); if (!objects) {mError = NO_MEMORY;return NO_MEMORY; } // Little hack to only acquire references on objects // we will be keeping. size_t oldObjectsSize = mObjectsSize; mObjectsSize = objectsSize; acquireObjects(); mObjectsSize = oldObjectsSize;}if (mData) { memcpy(data, mData, mDataSize < desired ? mDataSize : desired);}if (objects && mObjects) { memcpy(objects, mObjects, objectsSize*sizeof(size_t));}//ALOGI("Freeing data ref of %p (pid=%d)
", this, getpid());mOwner(this, mData, mDataSize, mObjects, mObjectsSize, mOwnerCookie);mOwner = NULL;mData = data;mObjects = objects;mDataSize = (mDataSize < desired) ? mDataSize : desired;ALOGV("continueWrite Setting data size of %p to %d
", this, mDataSize);mDataCapacity = desired;mObjectsSize = mObjectsCapacity = objectsSize;mNextObjectHint = 0; } else if (mData) {if (objectsSize < mObjectsSize) { // Need to release refs on any objects we are dropping. const sp<ProcessState> proc(ProcessState::self()); for (size_t i=objectsSize; i<mObjectsSize; i++) {const flat_binder_object* flat = reinterpret_cast<flat_binder_object*>(mData+mObjects[i]);if (flat->type == BINDER_TYPE_FD) { // will need to rescan because we may have lopped off the only FDs mFdsKnown = false;}release_object(proc, *flat, this); } size_t* objects =(size_t*)realloc(mObjects, objectsSize*sizeof(size_t)); if (objects) {mObjects = objects; } mObjectsSize = objectsSize; mNextObjectHint = 0;}// We own the data, so we can just do a realloc().if (desired > mDataCapacity) { uint8_t* data = (uint8_t*)realloc(mData, desired); if (data) {mData = data;mDataCapacity = desired; } else if (desired > mDataCapacity) {mError = NO_MEMORY;return NO_MEMORY; }} else { if (mDataSize > desired) {mDataSize = desired;ALOGV("continueWrite Setting data size of %p to %d
", this, mDataSize); } if (mDataPos > desired) {mDataPos = desired;ALOGV("continueWrite Setting data pos of %p to %d
", this, mDataPos); }} } else {// This is the first data. Easy!uint8_t* data = (uint8_t*)malloc(desired);if (!data) { mError = NO_MEMORY; return NO_MEMORY;}if(!(mDataCapacity == 0 && mObjects == NULL&& mObjectsCapacity == 0)) { ALOGE("continueWrite: %d/%p/%d/%d", mDataCapacity, mObjects, mObjectsCapacity, desired);}mData = data;mDataSize = mDataPos = 0;ALOGV("continueWrite Setting data size of %p to %d
", this, mDataSize);ALOGV("continueWrite Setting data pos of %p to %d
", this, mDataPos);mDataCapacity = desired; } return NO_ERROR;}1).整个读写全是在内存中进行,主要是通过malloc()、realloc()、memcpy()等内存操作进行,所以效率比JAVA序列化中使用外部存储器会高很多public class Book implements Parcelable{ private String bookName; private String author; private int publishDate;public Book(){ }public String getBookName(){return bookName; }public void setBookName(String bookName){this.bookName = bookName; }public String getAuthor(){return author; }public void setAuthor(String author){this.author = author; }public int getPublishDate(){return publishDate; }public void setPublishDate(int publishDate){this.publishDate = publishDate; }@Override public int describeContents(){return 0; }@Override public void writeToParcel(Parcel out, int flags){out.writeString(bookName);out.writeString(author);out.writeInt(publishDate); }public static final Parcelable.Creator<Book> CREATOR = new Creator<Book>(){ @Overridepublic Book[] newArray(int size){ return new Book[size];}@Overridepublic Book createFromParcel(Parcel in){ return new Book(in);} };public Book(Parcel in){//如果元素数据是list类型的时候需要: lits = new ArrayList<?> in.readList(list); 否则会出现空指针异常.并且读出和写入的数据类型必须相同.如果不想对部分关键字进行序列化,可以使用transient关键字来修饰以及static修饰.bookName = in.readString();author = in.readString();publishDate = in.readInt(); }}第一个Activity,MainActivityBook book = new Book();book.setBookname("Darker");book.setBookauthor("me");book.setPublishDate(20);Bundle bundle = new Bundle();bundle.putParcelable("book", book);Intent intent = new Intent(MainActivity.this,AnotherActivity.class);intent.putExtras(bundle);第二个Activity,AnotherActivity
Intent intent = getIntent();Bundle bun = intent.getExtras();Book book = bun.getParcelable("book");System.out.println(book);总结:Java应用程序中有Serializable来实现序列化操作,Android中有Parcelable来实现序列化操作,相关的性能也作出了比较,因此在Android中除了对数据持久化的时候需要使用到Serializable来实现序列化操作,其他的时候我们仍然需要使用Parcelable来实现序列化操作,因为在Android中效率并不是最重要的,而是内存,通过比较Parcelable在效率和内存上都要优秀与Serializable,尽管Parcelable实现起来比较复杂,但是如果我们想要成为一名优秀的Android软件工程师,那么我们就需要勤快一些去实现Parcelable,而不是偷懒与实现Serializable.当然实现后者也不是不行,关键在于我们头脑中的那一份思想。