If I have a ListView
with a CustomAdapter
and let's say I have this refresh()
method that refreshes the list with new results, should I:
Call new CustomAdapter(...)
upon initialization, and every time I call refresh()
, I use adapter.clear()
and adapter.add(...)
Call new CustomAdapter(...)
every time I call refresh()
Basically, I'm asking, is it better to recreate an adapter everytime I load new results or is it better to clear the results in existing adapter and add the entire list to it?
I think if you're going to use adapters as they were intended, then you'll update the adapter's data and call notifyDataSetChanged()
on it.
If you look at the API for something like ArrayAdapter, it has numerous methods like clear()
, add()
, addAll()
, notifyDataSetChanged()
and so forth that are there to guide you towards a certain use of the API.
By using these methods, not only does it make your code compliant with its intended usage, it also makes it easier to understand and familiar to others that are trying to understand your code.
So basically, I would only recreate the adapter as a last resort.
It is definitely better to call notifyDataSetChanged()
on the original adapter than setting a new one.
The reason is performance: ListView
uses view recycling to avoid creating new item views as you scroll. When you set a new adapter, these recycled views are discarded, which means they must be recreated from scratch for the next layout pass. Take a look at the code of ListView.setAdapter()
:
@Override
public void setAdapter(ListAdapter adapter) {
if (mAdapter != null && mDataSetObserver != null) {
mAdapter.unregisterDataSetObserver(mDataSetObserver);
}
resetList();
mRecycler.clear();
...
This is completely logical behavior, since the ListView
supposes that the views the new adapter will use are incompatible with the ones returned by the previous adapter (in any case, it cannot assume that they will be compatible). So they're thrown away.
Therefore, if you set a new adapter each time, you're incurring an unnecessary performance cost (recreating all the current views).
Also, if you wrote a custom adapter, you don't necessarily have to call add()
individually (as with, say, ArrayAdapter
). You can just replace the internal data collection with the new one and call notifyDataSetChanged()
afterwards.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With