【问题标题】:Should I throw an exception in constructors我应该在构造函数中抛出异常吗
【发布时间】:2019-06-15 22:44:02
【问题描述】:

如果我有一个三角形类,像这样:

export default class Triangle {

    sides: number[]

    constructor(...sides: number[]) {
        this.sides = sides
    }

    kind() {
        // returns type of triangle
    {
}

如果传入构造函数的边没有创建一个真正的三角形,是在创建类时(例如在构造函数中)还是在调用函数时抛出错误更好?

this answer,表示它在 Java 中没问题,而且我确信它在 TypeScript 中也有效。我只是想知道在一般的 OOP 和具体的 TypeScript 方面是否有“最佳实践”。

【问题讨论】:

    标签: typescript oop


    【解决方案1】:

    在构造函数中抛出是完全可以接受的。通常最好的做法是快速失败并尽早失败。例如,在您的情况下,最好在构造函数中抛出,以便错误可以及早暴露给负责发送错误数据的代码。如果您在实际使用三角形方法时稍后抛出,则将被该异常中断的代码没有错(他们无法采取不同的措施来防止异常)。这通常意味着您必须找到创建对象的位置,才能解决错误。

    首先,构造函数的主要职责之一是确保对象只能在有效状态下创建。因此,如果参数会导致对象处于无效状态,则抛出不仅是可以接受的,而且这也是构造函数存在的原因。

    【讨论】:

      【解决方案2】:

      没有正确的答案,但是您应该始终将“不可能”状态设为“不可能”来表示,IE 在这种情况下,三角形将始终具有 3 条边,因此只需将其之外的任意数量的边设置为无法通过即可。

      export default class Triangle {
          sides: number[]
          constructor(...sides: [number, number, number]) { // tuple now.
              this.sides = sides
          }
      }
      
      
      const test = new Triangle(2,2,2); // no error
      const test1 = new Triangle(2,2,2,2) // Error can't have 4 sides.
      

      这样做的好处是,只要传递了无效数量的参数,程序就会在编译时(安全)而不是运行时(不安全)失败

      【讨论】:

      • 这是一个很酷的解决方案,让我在验证中少了一件需要检查的事情。但是,我仍然需要抛出一个异常,好像你的答案支持在构造函数中做,太好了!
      猜你喜欢
      • 1970-01-01
      • 2013-05-20
      • 1970-01-01
      • 2011-11-04
      • 2014-11-03
      • 1970-01-01
      • 2019-03-11
      • 2017-02-09
      • 1970-01-01
      相关资源
      最近更新 更多