【问题标题】:Immutable class design不可变类设计
【发布时间】:2010-08-02 17:04:25
【问题描述】:

Joshua Bloch 给出的建议之一是,类应该设计为不可变的。

我有以下课程

public class Dividend {
    public Dividend setDate(SimpleDate date) {
        Dividend dividend = new Dividend(this.getStock(), this.getAmount(), date);
        return dividend;
    }
.....// More to go.

对于setDate 方法,this 对象不会被修改。

相反,将返回一个 this 的克隆副本,其日期字段已被修改。

但是,从方法名来看,用户怎么知道这个对象仍然是不可变的?

除了setDate还有更好的命名约定吗?

【问题讨论】:

  • Divident 是否有修改对象的setComment 方法?那么它就不是一成不变的。
  • 如果你的 setComment 方法是私有的,那么只有这个类是不可变的。
  • 你可以试试onDate/withDate/forDate等,而不是setDate
  • 我在这个例子中删除了 setComment 以避免混淆。

标签: java


【解决方案1】:

如果你有 setter,你的类看起来是可变的,用户可能会以错误的方式使用它。他们可能会这样称呼它:

dividend.setDate(myDate);

然后惊讶为什么dividend 的日期没有改变。他们应该这样使用它:

newDividend = dividend.setDate(myDate);

为了使 API 更直观,最好将 setDate 方法重命名为 copyWith 之类的名称:

newDividend = dividend.copyWith(myDate);

或者,如果您有很多字段并且重载会造成混淆,您可以将它们称为 copyWithDatecopyWithComment

其他名称也是可能的,如其他答案中所述:derive(和deriveWithDate),或者只是withDate

【讨论】:

    【解决方案2】:

    例如,Font 有 (a) derive 方法创建从当前字体派生的新字体实例。

    【讨论】:

    • 同意 - 我发现派生命名非常直观。
    【解决方案3】:

    我见过的许多 Java 库都开始使用 with 作为“此对象的副本, 进行以下更改”的前缀。

    例如:

    public Dividend withDate() {
       ....
    

    适合

    Dividend newDividend = oldDividend.withDate(...).withAmount(...).withComment(...);
    

    例如,JSR-310 遵循此模式(例如,将 plusXxx()minusXxx() 用于采用增量而非绝对值的“调整器”对象)。

    【讨论】:

      【解决方案4】:

      你应该像 String 类一样实现你的类,它上面没有设置器。可以理解,如果没有人可以在其上设置任何内容,则它是不可变的。 (也许您可能希望将 setter 设为私有,或者您可能只想直接从 Dividend 类内部设置变量)

      【讨论】:

        【解决方案5】:

        这个函数只是构造函数的一个包装器。重载构造函数以接受要复制的完整被除数对象。否则,您可以将此函数重命名为 getDividend(它绝对不是 setter)。

        【讨论】:

          【解决方案6】:

          由于返回了Dividend,用户可能会知道这是一个新的Dividend 实例。即便如此,您也可能会重新考虑这个名称。

          【讨论】:

          • 如果我不知道它是不可变的,我会假设它是一个流畅的界面并返回 this
          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2010-11-20
          • 1970-01-01
          • 2016-04-07
          相关资源
          最近更新 更多