0

状況は次のとおりです。2 つの異なる ID に基づいて、2 つのオブジェクトの一意性をテストしたいと考えています。例:

// Note I'm using JSON notation to keep things simple; the actual code 
// is with Java Objects

// OBJECT A
{
    main_id: 0,
    id_a: 123,
    id_b: 456
}

// OBJECT B
{
    main_id: 1,
    id_a: 123,
    id_b: 456
}

// OBJECT C
{
    main_id: 2,
    id_a: 123,
    id_b: 789
}

例では、オブジェクト A と B は、id_aid_bが同じであり、オブジェクト C が異なるため、同じです。

コードでこれを判断するために、両方の ID を文字列に変換し、それらを中間の区切り文字 (例: "{id_a},{id_b}") で連結し、それらを a に追加してSet<String>一意性をテストすることを計画しています。

私の質問は、より良い方法はありますか? (より良いとは、より効率的で、および/またはより厄介でないことを意味します)

4

3 に答える 3

2

を使用したい場合は、これらの 2 つのメンバーをHashSetオーバーライドhashCodeして排他的に見ることができます。equals

ハッシュコード: ( 31Java でハッシュに一般的に使用される素数です)

return 31*id_a + id_b;

Equals: (instanceofチェックと型変換を追加する必要があることは明らかです)

return id_a == other.id_a && id_b == other.id_b;

他の場所で別の方法で使用されているため、これらの関数をクラスにバインドしたくないが、それでも を使用したい場合はHashSet、次のことを検討できます。

  • セットに格納される中間クラスを作成します。これには、クラスがメンバーとして含まれ、上記のメソッドが適切に実装されます。

  • 文字列アプローチを使用する

  • Use HashSet<Point>-メンバーは単純にandPointと名付けられているため、座標以外の目的には理想的ではありませんが、少なくとも非運用コードでは、このようなクラスを利用できると便利です。xy


または、 を使用する場合TreeSetは、クラスに を実装Comparable(オーバーライドcompareTo) するか、Comparatorを提供することができますTreeSet。どちらも、主に 1 つの ID を比較し、次にもう 1 つの ID を比較します。

基本的な考え方は次のようになります。

if (objectA.id_a != objectB.id_a)
  return Integer.compare(objectA.id_a, objectB.id_a);
return Integer.compare(objectA.id_b, objectB.id_b);
于 2014-04-29T21:03:57.893 に答える
1

これを参照してください。ここでは、equals() と hashcode() をオーバーライドして、Person オブジェクトの「名前」フィールドの一意性を確保しています

public class SetObjectEquals {
    Person p1 = new Person("harley");
    Person p2 = new Person("harley");

    public void method1() {
        Set<Person> set = new HashSet<Person>();
        set.add(p1);
        set.add(p2);
        System.out.println(set);
    }

    public static void main(String[] args) {
        SetObjectEquals obj = new SetObjectEquals();
        obj.method1();
    }

}

class Person {
    String name;

    @Override
    public int hashCode() {
        final int prime = 31;
        int result = 1;
        result = prime * result + ((name == null) ? 0 : name.hashCode());
        return result;
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj)
            return true;
        if (obj == null)
            return false;
        if (getClass() != obj.getClass())
            return false;
        Person other = (Person) obj;
        if (name == null) {
            if (other.name != null)
                return false;
        } else if (!name.equals(other.name))
            return false;
        return true;
    }

    Person(String name) {
        this.name = name;
    }
}
于 2014-04-29T20:58:36.283 に答える