【问题标题】:Which is better practice, using private variables or public methods within the class?在类中使用私有变量或公共方法哪个更好?
【发布时间】:2017-04-27 21:47:51
【问题描述】:

例子:

private int x = 4;

public TestClass(int x) {
    this.x = x;
}

public TestClass(int x) {
    setX(x);
}

public void setX(int x) {
    this.x = x;
}

第一个构造函数更好还是第二个更好?我问这个是因为当我将我的类封装在IntelliJ IDEA 中时,如果我之前使用过this.x = x,它会将其更改为setX(int newX);

【问题讨论】:

  • 我通常更喜欢直接赋值,因为它节省了额外的堆栈操作。我通常只在具有比赋值更复杂的行为时才使用方法。
  • 可以说调用setX(int) 更不可预测,因为它可以被任何子类覆盖。 setX(int) 应该是 final 以防止这种情况;除非打算允许更改。
  • 我认为为每个字段制作 getter 和 setter 并简单地在包含类中访问它是一种矫枉过正的做法。所以我个人会坚持第一个例子this.x = x;。但当然可以说这取决于具体情况。
  • @OusmaneMahyDiaw 如果它需要读写,那么我不同意。
  • 强烈建议不要在 setter 中使用额外的逻辑,setter 应该只使用给定参数设置字段值 - 如果您需要额外的逻辑,请使用描述性名称调用方法。关于调用方法而不是直接访问该字段对额外的堆栈操作/轻微性能造成的影响 - 我认为实际上不会有任何影响,因为 JVM / JIT 优化,方法调用可以内联......

标签: java class methods setter


【解决方案1】:

在大多数情况下,这都是个人喜好。如果它的值不依赖于其他变量,我会使用第一个构造函数。但是,setter 方法允许在修改变量的值之前满足某些条件。例如:

private int x;

public TestClass(int x) {
    setX(x);
}

public void setX(int x) {
    // Some random condition depending on other variables.
    if (System.currentTimeMillis() & 1 == 0) {
        this.x = 5;
    } else {
        this.x = x;
    }
}

如果有许多条件不能用三元语句轻松表示,则使用 setter 方法是有意义的。

如果类是抽象的,那么扩展它的具体类可能会覆盖 setter 方法,从而修改变量的值。如果您打算使用自封装并且不希望任何子类覆盖 setter 方法,只需在方法声明中添加 final 关键字即可。

【讨论】:

    【解决方案2】:

    视情况而定。

    派生类可以覆盖setter,需要决定覆盖的效果在特定的地方是好是坏。

    我的观点是,如果 setter 被记录为可覆盖,则需要注意使用 setter 与赋值。如果您没有将设置器记录为可覆盖,则只需使用分配。

    【讨论】:

      【解决方案3】:

      有一个术语叫Self Encapsulation。 Martin Fowler 写了一篇关于这个主题的博客。 Blog Link。总而言之,有时您可能在setter 中有初始化或分配逻辑。所以我认为,每当您要初始化或分配值时,最好调用setter

      【讨论】:

      • 一篇非常有趣的博文。以前从未想过这个概念。谢谢!
      【解决方案4】:

      你已经接受了一个答案,但我仍然看到了一些没有人提到的东西。 setter 使您的类可变(至少没有保护条件),这可能是也可能不是一件好事。但是,如果将值提供给构造函数,则使您的类不可变会容易得多。

      不可变类本质上是线程安全的,只要可行,就应该首选。因此,在您的(诚然更简单的)示例中,我倾向于使用构造函数,并且我将只有一个获取值的方法。

      IMO,具有一个接受值的构造函数一个设置相同值的设置器,如果不是气味的话,就是代码香气。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2011-08-28
        • 1970-01-01
        • 2013-07-27
        • 1970-01-01
        • 2013-10-08
        • 2014-10-06
        • 2019-04-16
        • 2013-05-03
        相关资源
        最近更新 更多