1

私は一日中仕事をしてきましたが、どうにかしてこのおそらく簡単なタスクを理解することができません - おそらくコーヒーが不足しています...

synchronizedListいくつかのオブジェクトが保存されている場所があります。これらのオブジェクトにはfield、ID のようなものがあります。これらのオブジェクトは、ユーザーとその現在の状態 (簡略化) に関する情報を保持します。

ポイントは、ユーザーごとに 1 つのオブジェクトのみが必要だということです。したがって、このユーザーの状態が変化したときは、「古い」エントリを削除して新しいエントリを に保存したいと思いListます。

protected static class Objects{
    ...
    long time;
    Object ID;
    ... 
    }

...

if (Objects.contains(ID)) {
            Objects.remove(ID);
            Objects.add(newObject);
        } else {
            Objects.add(newObject);
        }

明らかにこれは進むべき道ではありませんが、私が探しているものを説明する必要があります...
おそらくデータ構造はこの目的には最適ではありませんが、どんな助けも大歓迎です!


EDIT:
いくつかの情報を追加しました...
ASetは私の目的に合わないようです。Objects常に変化する ID 以外のいくつかのフィールドを保存します。目的は、リストが何らかの形でユーザーの最新のアクティビティを表すことです。最後の状態を追跡し、この状況を説明するオブジェクトのみを保持する必要があるだけです。
コードを a で再配置してみて、それが機能するかどうかを確認しようと思いますMap...

4

5 に答える 5

3

IDのキーとObjectsの値でHashMap(または順序が重要な場合はLinkedHashMap / TreeMap)を使用できます。ジェネリックでHashMap<Object, Objects>();

その後、あなたは使用することができます

if (map.containsKey(ID)) {
    map.remove(ID);
}

map.put(newID, newObject);

または、リストを引き続き使用することもできますが、反復中にコレクションを変更することはできないため、代わりにイテレータを使用して既存のアイテムを削除し、ループの外に新しいアイテムを追加することができます(これで、古いアイテムがなくなっていることを確認してください):

List<Objects> syncList = ...

for (Iterator<Objects> iterator = syncList.iterator(); iterator.hasNext();) {
    Objects current = iterator.next();

    if (current.getID().equals(ID)) {
        iterator.remove();
    }
}

syncList.add(newObject);
于 2010-03-18T15:03:18.467 に答える
1

そして、セットを使用して最初のものだけを保存することはできませんか?

それは基本的にまさにあなたが必要とするものだからです。

于 2010-03-18T14:03:25.903 に答える
1

を使用してオブジェクトを格納し、 に含まれるクラスHashSetのメソッドをオーバーライドして、識別フィールドのハッシュコードを返すことができます。hashCodeHashSet

于 2010-03-18T14:03:34.630 に答える
0

私の最初のオプションはHashSetです。これには、同じ ID フィールドを持つオブジェクトが等しいと見なされるように、 hashCodeおよびequalsメソッドをオーバーライドする必要があります(忘れないでください: 一方をオーバーライドする場合は、もう一方を一貫してオーバーライドします!)。

ただし、アプリケーションの他の部分でこの仮定が行われない場合、これは何かを壊す可能性があります。その場合、HashMap (ID をキーとして) の使用を選択するか、独自のMyHashSetクラス (そのような HashMap に基づく) を実装することができます。

于 2010-03-18T14:42:29.107 に答える
0

マップは最も簡単ですが、セットはロジックをよりよく反映しています。その場合は、セットをお勧めします。

データ オブジェクトの equals と hashCode に応じて、セットを使用する方法は 2 つあります。

YourObject が既に ID オブジェクトを使用して equals を決定している (そして hashCode がコントラクトに従っている) 場合は、任意の Set を使用できます。その場合は HashSet がおそらく最適です。

ID フィールド以外の複数のフィールドを考慮して、YourObjects ビジネス ロジックで別の equals が必要な場合は、カスタム コンパレータを使用する必要があります。TreeSet は、そのような Comparator を使用できる Set です。

例:

Comparator<MyObject> comp = new Comparator<MyObject>{
  public int compare(MyObject o1, MyObject o2) {
    // NOTE this compare is not very good as it obeys the contract but
    // is not consistent with equals. compare() == 0 -> equals() != true here
    // Better to use some more fields
    return o1.getId().hashCode() < o2.getId().hashCode();
  }
  public boolean equals(Object other) {
    return 01.getId().equals(o2.getId());
  }
}

Set<MyObject> myObjects = new TreeSet(comp);

編集 質問で示唆されているように、idがintではないことを反映するように上記のコードを更新しました。

于 2010-03-18T14:03:31.207 に答える