2016-07-05 11 views
3

私はフィールドを持たないクラスをいくつか持っているとしましょう。たとえばのみinterfaceを実装するクラス:フィールドのないクラスのequals()の適切な実装とは何ですか?

public class SomeClass implements SomeInterface 
{ 
    @Override 
    public void someMethod(int param) {...} 

    @Override 
    public int getSomeValue(OtherClass param) {return ...;} 
} 

は、今私は、このためequals()を上書きしたいです。 trueを返すことはできますか?「オブジェクトには状態がないので、常に等しい」と主張することで、

このような実装:

@Override 
public boolean equals(Object other) 
{ 
    if (null == other || !(other instanceof SomeClass)) 
     return false; 
    return true; 
} 


編集:

一部の人々は、私はこの質問が生じている状況に、より詳しく説明するつもりだ、この背後にある意図について尋ねられたので、

このクラスはイベントリスナーです。私はそれをインスタンス化し、非同期要求へのリスナとして他のデータとともに、オブジェクトConfigにカプセル化して渡します。

つまり、という名前のクラスがあり、SomeClassと他のデータで構成されています。

public class Config 
{ 
    SomeClass someClass; 
    int otherData; 
    //... 

    @Override 
    public boolean equals(Object other) {/*???*/} 
} 

は実際に私が(私は再三の要求を防ぎたいので)この Configクラスの equalsを実装したかったです。しかし Configの1つの部分が SomeClassのこのインスタンスであるので、私はそれをどうするべきか考えていました。


サイド質問SomeClassが入れ子になったクラスであり、その外側のクラスの暗黙的な参照を持っている場合は、何をすべきか? (私の文脈では、それです。)

+7

なぜ、そのようなクラスに対して 'equals'をオーバーライドするのですか?おそらくそのクラスのインスタンスをSetまたはMapのキーに格納するつもりはありませんか? – Eran

+0

私はそれらが同じクラスのものである場合に限り同等であると言います。 'クラスOtherClassがSomeClassを拡張していて、いくつかのメソッドをオーバーライドした場合、それらは等しくあってはいけません。 –

+0

通常、私は静的メソッドを避けるために、反対を提唱しますが、クラスには**フィールドがない場合は何もしません。なぜ私は最初にそのクラスのインスタンスを作成する必要があるのだろうかと思っています。 – GhostCat

答えて

7

trueを返すだけでは、クラスのインスタンスがのいずれかの他のオブジェクトと等しいことを意味しますが、これはおそらく意図したとおりではありません。また、equalsの一般的なコミユニティ契約は、mySomeClass.equals("Mousa")trueを返し、"Mousa".equals(mySomeClass)falseを返すため、破棄されます。

SomeClassは状態を持たないため、そのequalsメソッドの実装は味わいの問題です。任意の2つのインスタンスを同じにすることは合理的な選択ですが、提案した実装を改善することはできます。other instanceof SomeClassothernullであれば、この方法は、ちょうどまた

@Override 
public boolean equals(Object other) { 
    return other instanceof SomeClass; 
} 

のように書き換えることができfalseを返すように、あなたは同じhashCode()を有する二つの等しいオブジェクトの一般的な契約を維持するために、あなたがする必要があることに注意してくださいそのメソッドもオーバーライドします。例:一方

@Override 
public int hashCode() { 
    return SomeClass.class.hashCode(); 
} 

、それはSomeClassは何の状態を持っていないので、それらの両方の点あれば、2つのオブジェクトが相互に等しくすることができる唯一の方法は、同じインスタンス(すなわちにあると判断することも完全に合理的です、 ==オペレータの動作)。このアプローチは、JDK-java.lang.Objectから知られる別の有名なステートレスクラスによって行われます。

+0

サブクラスでハッシュコードが失敗しますか? – matt

+0

@matt良い点。 'getClass()を使うとおそらく十分な弾力はありません。私はそれを改善するために私の答えを編集しました。 – Mureinik

+0

あなたの最初の段落について、私は私の実装でそれを考慮しました: 'if(null == other ||!(SomeClass)))falseを返す; – Mousa

4

これは意味論的な質問です。このクラスの2つのオブジェクトを持つことはどういう意味ですか? (それをシングルトンとして実装することも有用かもしれません)

これらは互換的に使用できれば、実際には同等と見なすことができます。 (hashCode()をオーバーライドすることを忘れないでください)しかし、同様に、Objectから来る元の定義を維持することができます。

+0

私は同意します。一歩踏み込んで...あなたは本当にステートレスクラスのインスタンスを複数必要としますか?なぜあなたは 'Collection'に複数のコピーを置いていますか、それともなぜそれらを比較していますか? – vikingsteve

+0

ありがとう、私はあなたの言うことを参照してください。実際にはこれは私の視点を変え、よりよく考えることができます。また、私は質問の文脈についての情報を追加しました。私はあなたの特定の事例についてあなたの意見を持っていたいと思います。 – Mousa

関連する問題