RecyclerView onBindViewHolder中if-else效率优化:第100项字号适配
更高效处理RecyclerView第100项字号的方案
嘿,这个问题问得特别务实——谁愿意在每次绑定视图时做99次无效判断呢?下面给你几个更高效的实现思路,完全不用每次都绕那个冗余判断:
1. 利用RecyclerView的多ViewHolder类型(最推荐)
RecyclerView本身就支持多布局类型,把第100项当成独立的视图类型来处理,从根源上避免判断:
- 首先定义两个视图类型常量:
private static final int TYPE_NORMAL = 0; private static final int TYPE_SPECIAL = 1; - 重写
getItemViewType方法,直接根据position区分类型(注意RecyclerView的position从0开始,第100项对应的position是99):@Override public int getItemViewType(int position) { return position == 99 ? TYPE_SPECIAL : TYPE_NORMAL; } - 在
onCreateViewHolder中,根据类型加载对应的布局(或者同一个布局里提前给特殊项的数字TextView设置好小字号):@Override public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) { if (viewType == TYPE_SPECIAL) { View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_special, parent, false); // 这里的item_special布局里,数字TextView已经预设好小字号 return new SpecialViewHolder(view); } else { View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item_normal, parent, false); return new NormalViewHolder(view); } } - 最后在
onBindViewHolder里,直接给对应类型的ViewHolder绑定数据即可,完全不需要额外判断——因为只有第100项会走到SpecialViewHolder的绑定逻辑。
这种方式完全贴合RecyclerView的设计初衷,性能最优,代码逻辑也最清晰。
2. 直接判断目标position(极简方案)
如果不想搞多类型,也可以把需要特殊处理的position做成常量,只在绑定该position时调整字号:
private static final int SPECIAL_POSITION = 99; @Override public void onBindViewHolder(@NonNull MyViewHolder holder, int position) { // 先绑定通用的条目描述数据 holder.description.setText(data.get(position).getDesc()); // 仅在目标position时调整字号 if (position == SPECIAL_POSITION) { holder.numberTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 12); // 假设小字号为12sp } else { holder.numberTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16); // 正常字号为16sp } holder.numberTextView.setText(String.valueOf(position + 1)); }
这里的判断是常量与变量的直接比较,JVM会自动做优化,实际开销几乎可以忽略,而且比判断数字是否等于100更直接(毕竟不需要从数据源里取出数字再做比较)。
3. 用SpannableString动态设置字号(适合动态数字场景)
如果你的数字不是固定从position+1生成,而是来自数据源的动态值,可以用SpannableString直接给“100”设置小字号,但同样只在必要时处理:
@Override public void onBindViewHolder(@NonNull MyViewHolder holder, int position) { Item item = data.get(position); String numberStr = String.valueOf(item.getNumber()); if (item.getNumber() == 100) { SpannableString spannable = new SpannableString(numberStr); spannable.setSpan(new AbsoluteSizeSpan(12, true), 0, 3, Spannable.SPAN_INCLUSIVE_INCLUSIVE); holder.numberTextView.setText(spannable); } else { holder.numberTextView.setText(numberStr); holder.numberTextView.setTextSize(TypedValue.COMPLEX_UNIT_SP, 16); } }
不过这个方案本质还是有判断,但如果数据源里只有一个100,其实判断的开销也微乎其微,只是代码上不如前两种简洁。
内容的提问来源于stack exchange,提问作者eric
相关产品推荐
相关产品推荐

