2017-01-02 43 views
0

我有一個基地class BaseNewsItem,和2派生類NewsItemMovieNewsItem。然後,有一個MovieListingFeed類,其中包含MovieNewsItem的列表,並且可以分類。它可以按照任何活動的要求將該列表打包。陷入泛型

protected MovieNewsListingFeed(Parcel in) { 
    this.pg = in.readParcelable(PageDetail.class.getClassLoader()); 
    this.items=new ArrayList<>(); 
    in.readTypedList(items, MovieNewsItem.CREATOR); 
} 

我收到錯誤的行:

in.readTypedList(items, MovieNewsItem.CREATOR); 

錯誤:

Error:(60, 11) error: method readTypedList in class Parcel cannot be applied to given types; required: List<T>,Creator<T> found: ArrayList<CAP#1>,Creator<CAP#2> reason: inferred type does not conform to equality constraint(s) inferred: CAP#2 equality constraints(s): CAP#2,CAP#1 where T is a type-variable: T extends Object declared in method <T>readTypedList(List<T>,Creator<T>) where CAP#1,CAP#2 are fresh type-variables: CAP#1 extends BaseNewsItem from capture of ? extends BaseNewsItem CAP#2 extends BaseNewsItem from capture of ? extends BaseNewsItem 

我在泛型新手,所以當我搜索上述錯誤,我沒有完全沒有發佈解決方案。我只是添加了,因爲我需要將ArrayList<MovieNewsItem>轉換爲ArrayList<BaseNewsItem>。從MovieNewsItem類

相關代碼:

public static final Creator<? extends BaseNewsItem> CREATOR = new Creator<MovieNewsItem>() { 
    public MovieNewsItem createFromParcel(Parcel source) { 
     return new MovieNewsItem(source); 
    } 

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

讓我知道是否需要任何進一步的代碼片段。

UPDATE 1:(readTypedList從Android框架。)

public final <T> void readTypedList(List<T> list, Parcelable.Creator<T> c) { 
    int M = list.size(); 
    int N = readInt(); 
    int i = 0; 
    for (; i < M && i < N; i++) { 
     if (readInt() != 0) { 
      list.set(i, c.createFromParcel(this)); 
     } else { 
      list.set(i, null); 
     } 
    } 
    for (; i<N; i++) { 
     if (readInt() != 0) { 
      list.add(c.createFromParcel(this)); 
     } else { 
      list.add(null); 
     } 
    } 
    for (; i<M; i++) { 
     list.remove(N); 
    } 
} 

MovieNewsListingFeed.java(問題文件):

public class MovieNewsListingFeed implements Parcelable { 

PageDetail pg; 

public void setItems(ArrayList<? extends BaseNewsItem> items) { 
    this.items = items; 
} 

ArrayList<? extends BaseNewsItem> items; 

public ArrayList<? extends BaseNewsItem> getItemsTemp() { 
    return itemsTemp; 
} 

public void setItemsTemp(ArrayList<? extends BaseNewsItem> itemsTemp) { 
    this.itemsTemp = itemsTemp; 
} 

ArrayList<? extends BaseNewsItem> itemsTemp; 

public ArrayList<? extends BaseNewsItem> getItems() { 
    return items; 
} 

public PageDetail getPg() { 
    return pg; 
} 


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

@Override 
public void writeToParcel(Parcel dest, int flags) { 
    dest.writeParcelable(this.pg, flags); 
    dest.writeTypedList(items); 
} 

public MovieNewsListingFeed() { 
} 

protected MovieNewsListingFeed(Parcel in) { 
    this.pg = in.readParcelable(PageDetail.class.getClassLoader()); 
    this.items = new ArrayList<>(); 
    in.readTypedList(items, MovieNewsItem.CREATOR); 
} 

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

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

}

MovieNewsItem.java:

public class MovieNewsItem extends BaseNewsItem implements Parcelable { 
String hl; 
String imageid; 
String syn; 
String id; 
String dm; 
String tn; 
String dl = ""; 
String sectionHeader; 
String upd; 
String ud; 

private int validListPosition = -1; 

public int getValidListPosition() { 
    return validListPosition; 
} 

@Override 
public void setTitle(String title) { 

} 

@Override 
public void setId(String id) { 

} 

@Override 
public void setDate(String date) { 

} 

@Override 
public void setNewsType(int newsType) { 

} 

public String getFormatedDate() { 
    return formatedDate; 
} 

String formatedDate; 

int position; 
int newSectionType = NewsType.CONTENT_TYPE_NEWS; 
String dayHeading; 

public int getPosition() { 
    return position; 
} 

public void setPosition(int position) { 
    this.position = position; 
} 


public void setNewSectionType(int newSectionType) { 
    this.newSectionType = newSectionType; 
} 

public String getDayHeading() { 
    return dayHeading; 
} 

public void setDayHeading(String dayHeading) { 
    this.dayHeading = dayHeading; 
} 

@Override 
public void setValidListPosition(int listPosition) { 

} 

public String getWu() { 
    return wu; 
} 

String wu; 


public String getHl() { 
    return hl; 
} 

public String getImageid() { 
    return imageid; 
} 

public String getSyn() { 
    return syn; 
} 

public String getId() { 
    return id; 
} 

public String getDm() { 
    return dm; 
} 

public String getTn() { 
    return tn; 
} 

public String getDl() { 
    return dl; 
} 

public String getSectionHeader() { 
    return sectionHeader; 
} 


public MovieNewsItem() { 
} 

@Override 
public String getTitle() { 
    return (!TextUtils.isEmpty(getSyn())) ? getSyn() : getHl(); 
} 

@Override 
public String getDate() { 
    return getFormatedDate(); 
} 

@Override 
public int getNewsType() { 
    return newSectionType; 
} 

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

@Override 
public void writeToParcel(Parcel dest, int flags) { 
    dest.writeString(this.hl); 
    dest.writeString(this.imageid); 
    dest.writeString(this.syn); 
    dest.writeString(this.id); 
    dest.writeString(this.dm); 
    dest.writeString(this.tn); 
    dest.writeString(this.dl); 
    dest.writeString(this.sectionHeader); 
    dest.writeString(this.upd); 
    dest.writeString(this.ud); 
    dest.writeInt(this.position); 
    dest.writeInt(this.newSectionType); 
    dest.writeString(this.dayHeading); 
    dest.writeString(this.wu); 
} 

protected MovieNewsItem(Parcel in) { 
    this.hl = in.readString(); 
    this.imageid = in.readString(); 
    this.syn = in.readString(); 
    this.id = in.readString(); 
    this.dm = in.readString(); 
    this.tn = in.readString(); 
    this.dl = in.readString(); 
    this.sectionHeader = in.readString(); 
    this.upd = in.readString(); 
    this.ud = in.readString(); 
    this.position = in.readInt(); 
    this.newSectionType = in.readInt(); 
    this.dayHeading = in.readString(); 
    this.wu = in.readString(); 
} 

public static final Creator<? extends BaseNewsItem> CREATOR = new Creator<MovieNewsItem>() { 
    public MovieNewsItem createFromParcel(Parcel source) { 
     return new MovieNewsItem(source); 
    } 

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

@Override 
public boolean equals(Object obj) { 
    MovieNewsItem newsItem = this; 
    if (obj instanceof MovieNewsItem) { 
     MovieNewsItem oldNewsItem = (MovieNewsItem) obj; 
     if (oldNewsItem != null && 
       newsItem.id.equals(oldNewsItem.id)) { 
      return true; 
     } 
    } 
    return false; 
} 

}

BaseNewsItem.java:

public abstract class BaseNewsItem implements NewsItemType { 

} 

NewsItemType.java:

public interface NewsItemType extends Parcelable { 
String getTitle(); 
String getId(); 
String getDate(); 
int getNewsType(); 
String getDayHeading(); 
int getValidListPosition(); 
int getPosition(); 

void setTitle(String title); 
void setId(String id); 
void setDate(String date); 
void setNewsType(int newsType); 
void setDayHeading(String dayHeading); 
void setValidListPosition(int listPosition); 
void setPosition(int position); 

}

+0

請添加**全部**相關代碼;例如'readTypedList()'。 – GhostCat

+1

什麼是「物品」的聲明?你正在向某個方法傳遞某些東西,編譯器會抱怨某些東西不能做;我們必須問你所有的細節...... – GhostCat

+1

你需要發佈一個[mcve] - 例如'items'的類型與你的問題非常相關,但是你沒有顯示它...... – assylias

回答

1

您的問題可以用這個小例子,被複制(由? extends BaseNewsItem和第二列表取代? extends Object通過Parcelable.Creator,你會看到邏輯完全相同):

public void test() { 
    List<? extends Object> a1 = new ArrayList<>(); 
    List<? extends Object> a2 = new ArrayList<>(); 
    m(a1, a2); //your compilation error here 
} 
public <T> void m(List<T> a1, List<T> a2) { } 

的問題是,通用型兩下表中是無關的:他們都擴展相同的基類,但是這就是我們知道他們 - 比如a1可能是List<String>a2一個List<Integer>

但是m方法期望兩個泛型類型是相同的 - 這不是你正在傳遞的。

所以你需要通過具有相同泛型類型的列表,例如:

public void test() { 
    List<SomeBaseClass> a1 = new ArrayList<>(); 
    List<SomeBaseClass> a2 = new ArrayList<>(); 
    m(a1, a2); //compiles fine 
} 
public <T> void m(List<T> a1, List<T> a2) { } 
0

這是由於類型不匹配 變化

ArrayList<? extends BaseNewsItem> itemsTemp; 

List<? extends BaseNewsItem> itemsTemp; 

更改方法是這樣的:

public final <T> void readTypedList(List<? extends BaseNewsItem> list, Parcelable.Creator<? extends BaseNewsItem> c) { 

}

希望它會工作。