2013-01-17 8 views
10

Ich bin kürzlich auf eine sehr dumme (zumindest aus meiner Sicht) Implementierung in Android Parcel Klasse gekommen.Wie writeStringArray() und readStringArray() in einem Paket

Angenommen, ich habe eine einfache Klasse, wie diese

class Foo implements Parcelable{ 

    private String[] bars; 
    //other members 

    public in describeContents(){ 
     return 0; 
    } 

    public void writeToParcel(Parcel dest, int flags){ 

     dest.writeStringArray(bars); 
     //parcel others 
    } 

    private Foo(Parcel source){ 
     source.readStringArray(bars); 
     //unparcel other members 
    } 

    public static final Parcelable.Creator<Foo> CREATOR = new Parcelable.Creator<Foo>(){ 

     public Foo createFromParcel(Parcel source){ 
      return new Foo(source); 
     } 

     public Foo[] newArray(int size){ 
      return new Foo[size]; 
     } 

    }; 
} 

Nun, wenn ich ein Foo Objekt Paket will und bars ist null Ich sehe keinen Weg aus dieser Situation zu erholen (außer von Ausnahmen natürlich zu kontrollieren) . Hier ist die Umsetzung dieser beiden Methoden von Parcel:

public final void writeStringArray(String[] val) { 
     if (val != null) { 
      int N = val.length; 
      writeInt(N); 
      for (int i=0; i<N; i++) { 
       writeString(val[i]); 
      } 
     } else { 
      writeInt(-1); 
     } 
    } 


    public final void readStringArray(String[] val) { 
     int N = readInt(); 
     if (N == val.length) { 
      for (int i=0; i<N; i++) { 
       val[i] = readString(); 
      } 
     } else { 
      throw new RuntimeException("bad array lengths"); 
     } 
    } 

So writeStringArray ist in Ordnung, wenn ich bars passieren, die null sind. Es schreibt einfach -1 in das Paket. Aber wie soll die Methode readStringArray verwendet werden? Wenn ich innen bars überlasse (was natürlich Null ist), bekomme ich eine NullPointerException von val.length. Wenn ich bars vorher wie sagen bars = new String[???] erstelle, erhalte ich keine Ahnung, wie groß es sein sollte. Wenn die Größe nicht mit dem Inhalt übereinstimmt, erhalte ich eine RuntimeException.

Warum ist readStringArray kein Ergebnis von -1 bekannt, das auf Nullobjekte von writeStringArray geschrieben wird und nur zurückgibt?

Die einzige Möglichkeit, die ich sehe, ist die Größe von bars zu speichern, bevor ich writeStringArray(String[]) anrufen, die diese Methode nutzlos macht. Es wird auch redundant die Größe des Arrays zweimal speichern (einmal für mich zu erinnern, das zweite Mal von writeStringArray).

Weiß jemand, wie diese beiden Methoden verwendet werden sollen, da es NO Java-Doc für sie oben gibt?

Antwort

28

Sie sollten Parcel.createStringArray() in Ihrem Fall verwenden.

Ich kann mir keinen richtigen Anwendungsfall für Parcel.readStringArray(String[] val) vorstellen, aber um es zu verwenden, müssen Sie die genaue Größe des Arrays kennen und manuell zuweisen.

+0

danke. merkt diese create * -Funktionen nie. Ich werde diese Frage immer noch ein wenig offen lassen, damit jemand mir einen Sinn für diese hässliche Methode geben kann. –

4

Es ist nicht wirklich klar aus der (fehlenden) Dokumentation, aber readStringArray() ist zu verwenden, wenn das Objekt bereits weiß, wie man das String-Array vor dem Aufruf dieser Funktion erstellt; zum Beispiel, wenn es statistisch instanziiert ist oder seine Größe von einem anderen vorher gelesenen Wert bekannt ist.

Sie müssen hier stattdessen die Funktion createStringArray() aufrufen.