Treeset克隆()的证明在java中创建浅拷贝?

时间:2016-08-23 11:02:42

标签: java shallow-copy

我有一个疑问,我想检查java中的TreeSet是否真的为它的clone()使用浅拷贝,但是根据我的程序,如果我从父树集中删除一个元素,它不会反映在它的克隆树集对象中。 / p>

public class TreeSetExample {
    public static void main(String[] args) {
        TreeSet<Name> nameTreeSet = new TreeSet<>();
        nameTreeSet.add(new Name("Compiere"));
        nameTreeSet.add(new Name("Aristotle"));
        nameTreeSet.add(new Name("CompierE"));
        nameTreeSet.add(new Name("COmpiere"));
        nameTreeSet.add(new Name("ArisTotle"));
        nameTreeSet.add(new Name("arisTotle"));
        nameTreeSet.add(new Name("aristotle"));
        System.out.println(nameTreeSet);

        TreeSet<Name> cloneNameTreeSet = (TreeSet<Name>) nameTreeSet.clone();
        System.out.println(nameTreeSet);
        Iterator<Name> itr = nameTreeSet.iterator();

        /*while (itr.hasNext()) {
            if (itr.next().getName().equals("aristotle"))
                itr.remove();
        }*/

        for(Name name: nameTreeSet) {
            if(name.getName().equals("aristotle"))
                nameTreeSet.remove(name);
        }

        System.out.println(nameTreeSet);
        System.out.println(cloneNameTreeSet);
    }
}

/*
*Name class which is used in my treeset to store its objects
*/

public class Name implements Cloneable, Comparable<Name>, Comparator<Name> {
    @Override
    public String toString() {
        return "Name [name=" + name + "]";
    }

    private String name;

    public Name(String name) {
        super();
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = 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;
        Name other = (Name) obj;
        if (name == null) {
            if (other.name != null)
                return false;
        } else if (!name.equals(other.name))
            return false;
        return true;
    }

    @Override
    public int compare(Name name1, Name name2) {
        return name1.name.compareTo(name2.name);
    }

    @Override
    public int compareTo(Name name) {
        return (this.name).compareTo(name.name);
    }

}

1 个答案:

答案 0 :(得分:4)

  

如果我从父树集中删除一个元素,它不会反映在它的克隆树集对象中。

你误解了浅拷贝意味着什么。这意味着对于TreeSet的每个元素,引用都将复制到新的TreeSet。因此,如果您改变位于一个Name中的Set个对象之一,则另一个Set中的相应元素也将被突变,因为它们都引用同一个对象。

例如,这会影响Set s:

    for(Name name: nameTreeSet) {
        if(name.getName().equals("aristotle"))
            name.setName("new name");
    }

但是,克隆的TreeSet是与原始TreeSet不同的对象,从一个元素中删除元素不会影响另一个元素。删除一个Set中的元素只会影响另一个元素而不是克隆您只需复制引用 - TreeSet<Name> cloneNameTreeSet = nameTreeSet;