为什么我可以在Typescript中设置getter属性的值?

时间:2018-04-25 13:55:53

标签: class typescript getter

让一个类只具有getter属性:

class Person {
  sureName: string = "";
  lastName: string = "";
  get name() {
    return `${this.sureName} ${this.lastName}`;
  }
}

我喜欢紧凑的C#初始化方式(例如string[] array = { "a1", "b1", "c1" };,这在Typescript中也是可能的。但是使用这种短类型语法,我被迫设置name属性:

let p: Person = {
  name: "xyz",
  sureName: "a",
  lastName: "b"
};
console.log(p); // { name: 'xyz', sureName: 'a', lastName: 'b' }

getter修饰符似乎完全被忽略了!为什么会出现这种奇怪的行为?使用new运算符时不是这种情况:

let p1 = new Person();
p1.name = "Peter"; // error TS2540: Cannot assign to 'name' because it is a constant or a read-only property.

这里从OOP视图中正确验证了getter。但与第一个相比,我真的不喜欢new operator:我没有设置所有必填字段的智能感知,我总是要输入对象名称作为前缀(p1.xyz)这很烦人当必须在命名良好的对象上设置多个属性时。

但是为了获得干净的OOP,我不得不使用new语法。或者停止使用C#之类的getter / setter,并使用getName()等方法。

1 个答案:

答案 0 :(得分:3)

不会忽略getter,如果您创建该类的实例,则存在getter。创建Person的实例意味着使用new运算符(即new Person())。您可以使用Person运算符

来测试您实际上并未创建instanceof的事实
let p: Person = {
  name: "xyz",
  sureName: "a",
  lastName: "b"
};
console.log(p instanceof Person); // will be false

您正在做的是创建一个与Person具有相同形状的对象文字(不是Person的实例)。由于它必须具有相同的形状(即相同的公共成员),因此它还必须具有name属性。 Typescript使用结构类型,所以这是允许的。有关详细信息,请参阅此answer

如果要创建新的Person并使用objet文字语法指定字段值,可以创建一个带有Partial<Person>参数的构造函数:

 class Person {
    constructor(value: Partial<Person>) {
        Object.assign(this, value);
    }
    sureName: string = "";
    lastName: string = "";
    get name() {
        return `${this.sureName} ${this.lastName}`;
    }
}

var p = new Person({
    sureName: "a",
    lastName: "b"
})