parcelable继承:抽象类 - 哪个CREATOR?

Pau*_*hek 8 java inheritance android parcelable

我有一个A实现Parcelable 的抽象类.

我有一个班级B和一个班级C都延伸A.我怎样才能使它们变得可以分辨?

因为我可以链接它并在许多帖子中提供CREATORin ABlike之类的建议.但由于我有其他对象存储A-B-C类并实现Parcelable自己,这种方法似乎不起作用,因为当我想传递一个ArrayList时,A我将不得不CREATOR在类型列表中使用

ArrayList<A> elements = new ArrayList<>();
in.readTypedList(elements , B.CREATOR); // B.CREATOR? C.CREATOR???
Run Code Online (Sandbox Code Playgroud)

这显然没有意义.那么我怎样才能正确制作A Parcelable?

即我想使这个类Parcelable所以我可以以一种常见的方式引用A.

一个)

public abstract class A implements Parcelable {

    final String globalVar;

    public A(String globalVar) {
        this.globalVar = globalVar;
    }
}
Run Code Online (Sandbox Code Playgroud)

B)

public class B extends A {

    String bVar;


    public B(String global, String bVar) {
        super(global);
        this.bVar = bVar;
    }

    private B(Parcel in) {
        super(in.readString());
        this.bVar = in.readString();
    }


    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel parcel, int i) {
        parcel.writeString(bVar);
    }
}
Run Code Online (Sandbox Code Playgroud)

C)

public class C extends A {

    String cVar;


    public C(String global, String cVar) {
        super(global);
        this.cVar = cVar;
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel parcel, int i) {
        parcel.writeString(cVar);
    }
}
Run Code Online (Sandbox Code Playgroud)

小智 11

我在这篇文章中使用了Vincent Mimoun-Prat的可分辨架构:Android中的Parcelable 和inheritance,遇到了必须指定一个不可能的抽象CREATOR的同一类型列表问题.

在Parcel的JavaDoc中搜索我发现了方法writeList(List val),它在内部对列表的每个对象使用writeValue(Object)方法,因此writeToParcel()从子类调用(B和C来自A列表).要解组列表,请使用其对应的readList(List outVal,ClassLoader loader),其中A ClassLoader必须传递或android.os.BadParcelableException抛出,至少在我的情况下.

包含A元素列表的类应该是这样的:

public class AContainer implements Parcelable {
    //Other AContainer fields
    List<A> elements = new ArrayList<>();
    //Other AContainer fields

    static final Parcelable.Creator<AContainer> CREATOR = new Parcelable.Creator<AContainer>() {
        @Override
        public AContainer createFromParcel(Parcel source) {
            return new AContainer(source);
        }

        @Override
        public AContainer[] newArray(int size) {
            return new AContainer[size];
        }
    };

    public AContainer() {
    }

    protected AContainer(Parcel source) {
        //read other AContainer fields
        source.readList(elements, A.class.getClassLoader());
        //read other AContainer fields
    }

    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(Parcel dest, int flags) {
        //write other AContainer fields
        dest.writeList(elements);
        //write other AContainer fields
    }
}
Run Code Online (Sandbox Code Playgroud)

使用这些方法可能会慢一些readTypedList(),writeTypedList()但是来自B和C子类的特定数据也被"分配",而不仅仅是来自A抽象超类的字段(它不可能是抽象的).您从B和C恢复正确的实例.


小智 -2

public class A implements Parcelable{\n\n       public A(){\n\n       }\n\n       public A(Parcel in){\n            super(in);\n           // read from parcel\n           // number = in.readInt() etc\n       }\n\n       @\xd0\x9everride\n       public int describeContents(){\n           return 0;\n       }\n\n       @Override\n       public void writeToParcel(Parcel dest, int flags) {\n           super.writeToParcel(out, flags);\n          // write to parcel\n          // out.writeInt\n       }\n       public static final Parcelable.Creator CREATOR = new Parcelable.Creator() {\n           public Student createFromParcel(Parcel in) {\n               return new A(in); \n           }\n\n           public A[] newArray(int size) {\n               return new A[size];\n           }\n       };\n   }\n
Run Code Online (Sandbox Code Playgroud)\n\n

B和C也必须实现Parcelable

\n