我应该在构造函数中使用 getter 和 setter 吗?

初始化类时,在构造函数中使用 getter 和 setter 函数是一种好习惯吗?

或者直接设置变量是一种好习惯,因为构造函数可以被认为是一种突变体?


慕容森
浏览 325回答 3
3回答

一只名叫tom的猫

您不应该从构造函数中调用 getter 和 setter。构造函数构造定义它的特定类。初始化字段是它的工作,因为 - 好吧 - 没有其他东西可以。保证初始化字段的唯一方法是分配它们。如果您调用 setter,则它可能会被覆盖,并且可能会执行其他操作。它可能会调用尚未初始化的子类中的方法。如果您只是从同一个类中获取一个字段,那么调用 getter 也是一个坏主意。如果它已在超类中声明,您可能会证明它是合理的;如果您需要在子类中从超类获取数据,则必须调用 getter(除非它受到保护)。如果您需要在构建过程中将数据从子类传递到超类,则应将其作为参数传递。但这与您所描述的用例不同,并且子类可能无论如何都没有您自己的与 getter 对应的字段。如果您有任何“特殊”初始化代码,请将其放在单独的私有方法中,并分别从构造函数和 setter 调用它。

白衣染霜花

这取决于,你是否打算继承这个类,其他人应该能够继承你的类吗?如果答案是否定的,那么您可以使用它,但我会说这样做通常是不好的做法,原因有几个,如果您没有明确禁止继承,那么可以对类进行子类化并重写方法,请参见下面的引用。一般来说,最好的做法是尽可能多地实现不变性,并且使用 getter/setter 可以防止你这样做。我还认为构造函数应该只具有将类初始化为有效状态所必需的参数。如果它们也可以使用 setter 传递,那么它们可能不是实现有效状态所必需的。如果你想在设计类时考虑到继承,那么答案是否定的,如果你使用 init 方法,它也不能使用 getter/setter,或者任何可以被覆盖的方法。来自 Effective Java 2nd Edition 的直接引用:一个类必须遵守更多的限制以允许继承。构造函数不得直接或间接调用可覆盖的方法。如果您违反此规则,将导致程序失败。超类构造函数在子类构造函数之前运行,因此子类中的覆盖方法将在子类构造函数运行之前被调用。如果覆盖方法依赖于子类构造函数执行的任何初始化,则该方法将不会按预期运行。

墨色风雨

我看到的方式是,当构造函数定义类时,我可以使用 setter 来检查参数和/或将它们初始化为某些值。在我有一个计算变量的情况下,我也可以使用 getter,但我应该非常小心语句的顺序(不建议容易出错)。JavaScript 中的示例:class Point {&nbsp; constructor (x, y) {&nbsp; &nbsp; this.x = x.x || x // invokes the setter&nbsp; &nbsp; this.y = x.y || y&nbsp; }&nbsp; toString () {&nbsp; &nbsp; return `The point is (${this.x}, ${this.y})` // invokes the getters&nbsp; }&nbsp; set x (newX) { // I think it should be better use 'newX' as a parameter than 'x'&nbsp; &nbsp; if (newX > 100) {&nbsp; &nbsp; &nbsp; console.log(`The x (${newX}) value must be < 100, `, 'x set to 0')&nbsp; &nbsp; &nbsp; this._x = 0 // if we use 'this.x' here, we will get an error (stack overflow)&nbsp; &nbsp; &nbsp; return&nbsp; &nbsp; }&nbsp; &nbsp; this._x = newX&nbsp; }&nbsp; get x () { // no one but the getter and setter should know '_x' exists&nbsp; &nbsp; return this._x // it has to be coherent with the setter&nbsp; }&nbsp; set y (newY) {&nbsp; &nbsp; if (newY > 100) {&nbsp; &nbsp; &nbsp; console.log(`The y (${newY}) value must be < 100, `, 'y set to 0')&nbsp; &nbsp; &nbsp; this._y = 0&nbsp; &nbsp; &nbsp; return&nbsp; &nbsp; }&nbsp; &nbsp; this._y = newY&nbsp; }&nbsp; get y () {&nbsp; &nbsp; return this._y&nbsp; }}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Java