我正在学习RecyclerView,在developer的站点中,Adapter类扩展了RecyclerView.Adapter<MyAdapter.MyViewHolder>
。实现显示:
public class MyAdapter extends RecyclerView.Adapter<MyAdapter.MyViewHolder> {
private String[] mDataset;
public static class MyViewHolder extends RecyclerView.ViewHolder {
public TextView textView;
public MyViewHolder(TextView v) {
super(v);
textView = v;
}
}
public MyAdapter(String[] myDataset) {
mDataset = myDataset;
}
@Override
public MyAdapter.MyViewHolder onCreateViewHolder(ViewGroup parent,
int viewType) {
TextView v = (TextView) LayoutInflater.from(parent.getContext())
.inflate(R.layout.my_text_view, parent, false);
MyViewHolder vh = new MyViewHolder(v);
return vh;
}
@Override
public void onBindViewHolder(MyViewHolder holder, int position) {
holder.textView.setText(mDataset[position]);
}
@Override
public int getItemCount() {
return mDataset.length;
}
}
并且在此tutorial中,适配器类扩展了RecyclerView.Adapter
。实现是:
public class SimpleAdapter extends RecyclerView.Adapter {
private List<SimpleViewModel> models = new ArrayList<>();
public SimpleAdapter(final List<SimpleViewModel> viewModels) {
if (viewModels != null) {
this.models.addAll(viewModels);
}
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(final ViewGroup parent, final int viewType) {
final View view = LayoutInflater.from(parent.getContext()).inflate(viewType, parent, false);
return new SimpleViewHolder(view);
}
@Override
public void onBindViewHolder(final RecyclerView.ViewHolder holder, final int position) {
((SimpleViewHolder) holder).bindData(models.get(position));
}
@Override
public int getItemCount() {
return models.size();
}
@Override
public int getItemViewType(final int position) {
return R.layout.item_simple_itemview;
}
}
那么RecyclerView.Adapter<MyAdapter.MyViewHolder>
和RecyclerView.Adapter
之间有什么区别?在这种情况下,RecyclerView.Adapter<MyAdapter.MyViewHolder>
中的语法<>是什么意思?我知道它代表泛型。我什么时候应该使用它?
那么RecyclerView.Adapter
和RecyclerView.Adapter有什么区别?在这种情况下,RecyclerView.Adapter中的语法<>是什么?我知道它代表泛型。我什么时候应该使用它?
首先,让我们回顾一下Adapter
类的定义。它在RecyclerView
中的定义如下:
public abstract static class Adapter<VH extends ViewHolder>
那么,“泛型”部分是什么意思?这意味着Adapter类对某些类类型(VH
)进行操作,该类类型必须是类ViewHolder
的后代。这称为Bounded Type,并确保适配器正在使用的类的类型保证为ViewHolder
的类型。
正如您在发布的开发人员网站上的示例中所看到的那样,当创建自己的适配器以将ViewHolder的类型指定为MyViewHolder
时,必须在适配器中重写的方法在其签名中显式声明该类型。 。例如,onCreateViewHolder
的返回类型显式设置为MyViewHolder
。
指定类型。@Override public MyAdapter.MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { TextView v = (TextView) LayoutInflater.from(parent.getContext()) .inflate(R.layout.my_text_view, parent, false); MyViewHolder vh = new MyViewHolder(v); return vh; }
或者,您发布的教程没有[[not
public class SimpleAdapter extends RecyclerView.Adapter
当扩展一个需要通用类型的类而未指定一个类型时,-也就是说,在继承层次结构中最低的类类型将保证该类可以是按设计使用。因为适配器的通用类型定义为编译器默认为最小公分母
VH extends ViewHolder
,所以编译器知道类类型必须为[[至少 a ViewHolder
,并且默认为该类型。因此,在此示例中重写的相同方法将返回RecyclerView.ViewHolder
而不是MyViewHolder
:@Override
public RecyclerView.ViewHolder onCreateViewHolder(final ViewGroup parent, final int viewType) {
final View view = LayoutInflater.from(parent.getContext()).inflate(viewType, parent, false);
return new SimpleViewHolder(view);
}
如果RecyclerView.Adapter
被定义为Adapter<VH>
(无边界类型),并且在未指定类型的情况下对其进行了扩展,则该类型将默认为Object
(所有Java类的根类):@Override public Object onCreateViewHolder(final ViewGroup parent, final int viewType) { final View view = LayoutInflater.from(parent.getContext()).inflate(viewType, parent, false); return new SimpleViewHolder(view); }
所以,最后,为什么要使用一个而不是另一个?一般而言:。这样可以保证您的类型安全。在本教程示例中,您可能返回错误的视图持有者类型,该类型的视图持有者会编译但在运行时崩溃:
您应始终为通用类指定类型
@Override
public RecyclerView.ViewHolder onCreateViewHolder(final ViewGroup parent, final int viewType) {
final View view = LayoutInflater.from(parent.getContext()).inflate(viewType, parent, false);
// Returning wrong view holder, but because it still extends ViewHolder and
// that is all this method requires, this compiles
return new SomeOtherViewHolder(view);
}
@Override
public void onBindViewHolder(final RecyclerView.ViewHolder holder, final int position) {
// Above we created a SomeOtherViewHolder but here we're expecting a SimpleViewHolder
// This will crash trying to cast to the wrong type
((SimpleViewHolder) holder).bindData(models.get(position));
}
ViewHolder
类型是显式声明的:类型,所以您不会意外返回错误的类型,不需要强制转换,并且可以利用自定义[ C0]类。希望有帮助!@Override public MyAdapter.MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { TextView v = (TextView) LayoutInflater.from(parent.getContext()) .inflate(R.layout.my_text_view, parent, false); // Trying to return SomeOtherViewHolder when method expects MyViewHolder // Compiler's like (*waves finger*) "nuh-uh, not on my watch" and fails // to compile SomeOtherViewHolder vh = new SomeOtherViewHolder(v); return vh; } @Override public void onBindViewHolder(MyViewHolder holder, int position) { // Notice here that holder is explicitly of MyViewHolder type and casting // is not necessary! That's TYPE SAFETY y'all. holder.textView.setText(mDataset[position]); }
因为您指定了期望的
explicit,concrete