我正在看打字手册,在界面一章,我发现了一个问题:

interface LabelledValue {
  label: string;
}

function printLabel(labelledObj: LabelledValue) {
  console.log(labelledObj.label);
}

let myObj = {size: 10, label: "Size 10 Object"};
printLabel(myObj);

printLabel需要一个具有label:string属性的对象,但是我们传递的对象有另一个名为size的属性。这是可以的,因为编译器只检查是否至少存在所需的类型,并匹配所需的类型。
但是,我这样称呼printLabel
printLabel({size: 10, label: "Size 10 Object"});

编译抛出异常。
为什么?

最佳答案

文档已过时且an issue exists to fix it
What's New in TypeScript page开始:
TypeScript1.6强制执行更严格的对象文字赋值检查,以捕获多余或拼写错误的属性。特别是,当新的对象文本被分配给变量或作为非空目标类型的参数传递时,对象文本指定目标类型中不存在的属性是错误的。
其思想是,这是一个非常常见的模式,即将对象文本作为选项包传入。例如:

interface ConnectionOptions {
    tryHttps?: boolean;
    url?: string;
    username?: string;
    password?: string;
}

但所有这些属性都是可选的。在1.6之前,我可能会拼错其中任何一个,编译器永远不会捕捉到这个错误:
declare function connect(options: ConnectionOptions);

// Notice the property given is 'tryHTTPS' instead of 'tryHttps'.
connect({ url: "stackoverflow.com", tryHTTPS: true });

您可以通过向要分配给的类型添加类型断言来解决此问题:
printLabel({size: 10, label: "Size 10 Object"} as LabelledValue);
// or...
printLabel(<LabelledValue>{size: 10, label: "Size 10 Object"});

09-19 17:29