为什么我们需要这种特殊类型的构造函数?

时间:2015-03-20 10:11:37

标签: java constructor domain-object

public MyConstructor(MyConstructor mc){
   this.setId(mc.getId());
   this.setName(mc.getName());
}

为什么我们需要通过获取其getter方法在构造函数中设置值。这背后有什么特别的目的吗?

4 个答案:

答案 0 :(得分:1)

正如其他答案中已经指出的那样,这种构造函数主要用于克隆对象,有时称为复制构造函数

正如Joshua Bloch在他的书“ Effective Java ”第11项中所建议的那样,这种构造函数通常应优先于实现clone()方法,因为clone()方法有一些问题(有关详细信息,请参阅本书或相应的stackoverflow问题)。

实现它完全相同没有明显的理由 - 因此, 正如评论中所提到的,人们可以(最有可能)将其写为

public MyConstructor(MyConstructor mc){
    this.id = mc.getId();
    this.name = mc.getName();
}

public MyConstructor(MyConstructor mc){
    this.setId(mc.id);
    this.setName(mc.name);
}

public MyConstructor(MyConstructor mc){
    this.id = mc.id;
    this.name = mc.name;
}

此处作者选择使用嵌套set(mc.get())方法。它具有潜在的优势,它仅依赖于根据get / set方法定义的接口,因此可能对更改更具鲁棒性。

有人可能会争论这是否是一般的好习惯,但我认为对于复制构造函数,它很好地清楚地说明:“这个对象在这里初始化,完全基于(并且完全像)给定对象”


附注:克隆一个对象并给克隆提供相同的ID最有可能击败 ID 的purpouse - 但可能会出现这种情况

答案 1 :(得分:0)

考虑暂时克隆对象,但这不是克隆。如果您遇到手中有MyConstructor(类型)对象并且需要使用相同对象类型MyConstructor创建另一个对象的情况。所以,在你的MyConstructor类中,你需要一个像上面这样的构造函数。

您可以将对象拿在手中,然后使用该对象的 id 创建全新的第二个对象

答案 2 :(得分:0)

这样的构造函数背后的目的主要是用于克隆。 假设您需要将一个对象的值分配给另一个而不是引用,这将正常工作。

这里已经讨论过了: How do I copy an object in Java?

答案 3 :(得分:0)

如果您的类将由(子)类派生,这一点非常重要。

public class Child extends Parent {

    private int id;
    private String name = "Child";

    ...
    // getter and setters...
}


public class Parent {

    private int id;
    private String name = "Parent";

    public Parent(Parent parent) {
        this.setId(parent.getId());
        // option#1
        this.setName(parent.getName());
        // option#2
        // this.name = parent.name;
    }
    ...
    // getter and setters...
}

示例主要:

public class Main {
    public static void main(String ...strings ) {

        Parent parent = new Parent();
        Child child = new Child();

        Parent parent2 = new Parent(child);
        System.out.println(parent2.getName());

    }
}

输出:

Child

但如果我们使用选项#2 this.name = parent.name而输出将是

Parent