簡體   English   中英

在Java中使用繼承等同有什么問題?

[英]What's wrong with using Inheritance Equality in Java?

在我正在閱讀的“ 核心Java卷1 ”一書中,它說平等不應該與繼承一起使用。 所以,我有以下示例,似乎有一些錯誤:

public class Main {

    public static void main(String[] args) {

        C c = new C("Test", 10);
        D d = new D("Test", 10);

        if (c.equals(d))
            System.out.println("Equal");
        else
            System.out.println("Unequal");

        if (d.equals(c))
            System.out.println("Equal");
        else
            System.out.println("Unequal");
    }
}


class C
{
    C(String cstr, int cnum) {
        str = cstr;
        num = cnum;
    }

    @Override
    public boolean equals(Object otherObject) {

        // A quick test to see if the objects are identical.
        if (this == otherObject) {
            return true;
        }

        // Must return false if the explicit parameter is null
        if (otherObject == null)
        {
            return false;
        }

        if (!(otherObject instanceof C))
            return false;

        // Now we know otherObject is a non-null Employee
        C other = (C) otherObject;

        // Test whether the fields have identical values
        return str.equals(other.str) && num == other.num;
    }

    private String str;
    private int num;
}

class D extends C {

    D(String cstr, int cnum) {
        super(cstr, cnum);
    }
}

http://ideone.com/PhFBwG

對於兩個對稱比較,它返回“等於”,這可能是不應該的。 是否在派生類'D'中缺少另一個equals方法? 如果是這樣的話,那么上面的示例代碼可能會出現什么問題,如果我不使用另一個equals派生它?

如果您希望實例CD不與otherObject.getClass() != this.getClass()進行相等替換!(otherObject instanceof C) otherObject.getClass() != this.getClass() 這將確保只有C可以等於另一個C並且只有D可以等於另一個D

這是否是你想要的取決於幾個因素。 我的一般經驗法則是,擁有一個“開放式”平等類是一個壞主意,“外部用戶”(無論對你來說意味着什么)可以添加到它。 如果您希望將不同類型的對象比較為相等(並且這種情況非常罕見),則應嚴格控制層次結構(例如,使用final類)。

集合(和類似的明確定義的接口)是不同的:這里接口定義了一個非常精確的契約,所有實現類都需要遵循它(即如果它們都以相同的順序包含相同的元素,則ArrayList可以等於LinkedList ,因為List接口定義了兩個List s相等的含義。

該代碼有效,因為正如您所說, D不會覆蓋equals 我希望本書所提出的觀點是D 應該重寫equals (並且它們都應該覆蓋hashCode ),因為D實例不應該等於C實例,因為它們是不同的(盡管是相關的)類型。

請記住, equals合同的一個關鍵方面是對稱性 對於cd任何非null值,如果c.equals(d)為真,則d.equals(c)必須為真(和相反)。 雖然在你當前的代碼中也是如此,但它可能不應該是,因為DC是不同的類型。 如果D實例真的等同C實例,為什么有D

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM