7

有一个我遇到的问题

public class Student{
     private String studentNumber;
     private String studentName;
     private double studentResult;

     public Student (String aNumber, String aName){
         setStudentNumber(aNumber);
         setStudentName(aName);
         setStudentResult(0);
     }
     // The standard getter and setter method are define here.
}

在构造函数中使用 setter 方法的目的是什么?并且使用 setStudentResult(0),我们是否需要另一个实例变量?

4

6 回答 6

5

调用可覆盖的方法是一种反模式,如果 Student 被覆盖,它可能会导致问题。一个好的模式是让 Student 不可变

public class Student{
    private final String studentNumber;
    ...
    public Student (String studentNumber, ...) {
       this.studentNumber = studentNumber;
    ...
于 2013-04-23T11:04:06.543 回答
3

构造函数中设置器的通常声称的原因是您使用相同的验证。然而,自封装是一种反模式。

更好地完成您所写的事情是拥有一个构造对象并调用 set 方法的静态方法。比这更好的是使整个事物不可变。

于 2013-04-23T11:05:10.137 回答
1

sent当您处理(您正在发送的)值的验证时,您将不得不使用上述代码实践。
例如,如果您不想允许将任何负数设置为studentNUmber来自构造函数的 a,那么您必须编写一个逻辑来检查构造函数内部或方法内部的数字,具体取决于类是不可变的还是可变的。如果类是可变的,则在方法中编写逻辑,如果类是不可变的,则在构造函数中编写逻辑(在不可变的类中,不允许编写 setter 方法,因为 setter 方法可以更改对象的状态)。
如果您不应用此类逻辑,则可以将任何负值设置为studentNumber.

此外,当您在其他类中创建了一个对象并且稍后您想要更改它的状态时,setter 方法很有用,例如,您想要更新学生的姓名,如下面给出的示例,

public class Student {
    private String studentNumber;
    private String studentName;
    private double studentResult;
    // The standard getter and setter method are define here.

    public Student(String aNumber, String aName) {
        studentNumber = aNumber;
        studentName =aName;
    }

    public String getStudentNumber() {
        return studentNumber;
    }

    public void setStudentNumber(String studentNumber) {
        this.studentNumber = studentNumber;
    }

    public String getStudentName() {
        return studentName;
    }

    public void setStudentName(String studentName) {
        this.studentName = studentName;
    }

    public double getStudentResult() {
        return studentResult;
    }

    public void setStudentResult(double studentResult) {
        this.studentResult = studentResult;
    }

    @Override
    public String toString() {
        return "studentNumber:"+studentNumber+", studentName"+studentName+", studentResult"+studentResult;
    }

}

class Test {
    public static void main(String[] args) {
        Student s = new Student("1", "AAA");
        s.setStudentName("BBB"); //we should call this method because of "studentName" is private variable in Student class.
        System.out.println(s);
    }
}

about setStudentResult,你不需要另一个实例变量,因为它已经在Student类中声明了。相反,您需要在构造函数中再添加一个参数来setStudentResult赋值。

public Student(String aNumber, String aName, long result) {
        studentNumber = aNumber;
        studentName =aName; 
        studentResult =result;
    }
于 2013-04-23T11:03:29.933 回答
1

您是否在 setter 方法中执行任何业务逻辑。如果是,我想这就是你从构造函数调用 setter 的原因。如果您只是在 setter 中看到实例变量,那么直接设置实例变量是正常的做法。

public class Student{
private String studentNumber;
private String studentName;
private double studentResult;

public Student (String aNumber, String aName){
this.studentNumber = aNUmber;
this.studentName=aName;
this.studentResult=0;
}
于 2013-04-23T11:04:20.273 回答
0

如前所述,在构造函数中使用 setter 方法并不是一个好主意,原因有两个:

  1. 子类可以覆盖它们,这可能会使对象处于未被考虑的状态。

  2. setter 方法可以具有通常在构造函数中可能不需要的功能。

这样做的原因有两个:

  1. 大多数情况下,如果您在编写构造函数后生成 setter/getter,IDE(例如 eclipse)会自动执行此操作。

  2. 有时,setter 方法也会执行您在使用构造函数进行初始化时想要执行的验证或格式化。在这种情况下,我建议将验证/格式化提取到不同的函数中,并从构造函数和设置器中调用该函数。

于 2013-04-23T11:11:20.467 回答
0

从构造函数调用方法不是一个好主意。构造函数用于设置字段的初始值。

如果您想从构造函数中调用方法并且不希望有人覆盖它。将类声明为 final

于 2013-04-23T11:04:36.580 回答