3

ListViewコンテンツをフィルタリングするためのメソッドを実装します。どのような場合に使用する必要があるか詳しく教えていただけますか?

私が理解しているように、そのようなフィルタリングは配列ベースのアダプターに適しています-すべてのデータはすでにメモリ内にあります。このように、フィルターは表示されるべきではないデータをスキップするのに役立ちます。

ただし、ListViewカーソル アダプタ (SQLite データベース) を使用して多数のアイテムを表示すると、データがメモリにない場合があります。一方、フィルター値を SQL クエリに埋め込むと、削減されたデータ セットを効果的に取得できます。

のフィルタリング メカニズムはListView、カーソル ベースのデータ用にも設計されましたか? を使用するFilterable必要がある場合と、ListView フィルターを使用せずにフィルターを SQL クエリに渡す必要がある場合はいつですか? このアプローチまたはそのアプローチを使用する必要がある場合に推奨事項はありますか?

ありがとう

PS質問は、URIのシステムをどのように設計する必要がありますか?から分離されました。それは以前の2つを組み合わせたものです。

4

2 に答える 2

2

両方のメリットを享受できます。を設定しますFilterが、データベースに対してまったく新しいクエリを実行しないrunQuery()でください。FilterQueryProvider元のカーソルの周りにラッパーを使用して、不要なものを除外します。このラッパーの作成は比較的簡単で、SO でも言及されています。

最近の経験から: 両方を使用しないでください。Filterable独自のバックグラウンド処理を行うため、使用する場合はまったく必要ありませんCursorLoader。実際には、両方を使用しても実際に害はありませんが、不要なクエリが発生し、パフォーマンスが低下します。クエリrunQuery()は、フィルターなし (制約が空) とフィルター済み (制約が空でない) の両方のケースを処理する必要があります。つまり、すべてのクエリ操作はフィルターを介して実行され、フィルターのみが実行されます。開始するために必要なのは、アダプターのコンストラクターでこれを呼び出すことだけです。

setFilterQueryProvider(this);
getFilter().filter(null);

そして、頭痛の種になった厄介な驚き。CusorLoader厳密なモードでも問題はありませんが、カーソルをかなりうまく管理しますがFilterable、状況は完全ではありません。通常の操作では問題ありません。古いカーソルは破棄されますが、アクティビティのライフサイクルの変更により、それが検出される可能性があります。私が見つけた解決策は、これらのアダプターで使用するビューを拡張ListView/RecyclerViewし、カーソルが最後に破棄されるようにすることです。

@Override
protected void onDetachedFromWindow() {
  super.onDetachedFromWindow();
  ((CursorAdapter) getAdapter()).changeCursor(null);
}

別の方法として、拡張したくない場合は、onDestroy()アダプターに基づくビューごとにアクティビティから同じものを呼び出すことができますが、私は最初のアプローチが提供する設定して忘れるアプローチを好みます。

于 2014-12-29T11:26:10.207 に答える