将具有可为空字符串 属性 的接口转换为字符串 属性
Convert interface with nullable string property to string property
我有以下两个接口,一个允许可空 vin
,另一个不允许:
interface IVehicle {
vin: string | null;
model: string;
}
interface IVehicleNonNullVin {
vin: string;
model: string;
}
我希望能够在我能够推断 vin
不是 null
的执行路径中将模型从 IVehicle
转换为 IVehicleNonNullVin
。
考虑这个例子:
const myVehicle: IVehicle = {
vin: 'abc123',
model: 'm3'
};
const needsVin = (_: IVehicleNonNullVin) => false;
if (myVehicle.vin === null) {
throw new Error('null');
} else {
needsVin(myVehicle);
// ~~~~~~~~~~~~~~~~~~~ 'IVehicle' is not assignable to 'IVehicleNonNullVin'
}
其中returns出现以下错误:
Argument of type 'IVehicle' is not assignable to parameter of type 'IVehicleNonNullVin'.
Types of property 'vin' are incompatible.
Type 'string | null' is not assignable to type 'string'.
Type 'null' is not assignable to type 'string'.
即使我 阳性 属性 在这里也不可为空。
Q: 如何让TS相信现有模型符合代码流中基于类型检查的类型?
Demo in TS Playground
解决方法
作为变通方法,我可以转换类型(但这会忽略现有的类型安全):
needsVin(myVehicle as IVehicleNonNullVin);
或构建一个新模型(但这不能很好地扩展大量属性):
const nonNullVehicle: IVehicleNonNullVin = {
model: myVehicle.model,
vin: myVehicle.vin
}
needsVin(nonNullVehicle);
您可以使用 type predicate 来定义用户定义的类型保护,如下所示:
const isNonNullVin = (vehicle: IVehicle): vehicle is IVehicleNonNullVin =>{
return vehicle.vin !== null
}
if (!isNonNullVin(myVehicle)) {
throw new Error('null');
} else {
needsVin(myVehicle);
}
TypeScript will narrow that variable to that specific type if the original type is compatible.
我有以下两个接口,一个允许可空 vin
,另一个不允许:
interface IVehicle {
vin: string | null;
model: string;
}
interface IVehicleNonNullVin {
vin: string;
model: string;
}
我希望能够在我能够推断 vin
不是 null
的执行路径中将模型从 IVehicle
转换为 IVehicleNonNullVin
。
考虑这个例子:
const myVehicle: IVehicle = {
vin: 'abc123',
model: 'm3'
};
const needsVin = (_: IVehicleNonNullVin) => false;
if (myVehicle.vin === null) {
throw new Error('null');
} else {
needsVin(myVehicle);
// ~~~~~~~~~~~~~~~~~~~ 'IVehicle' is not assignable to 'IVehicleNonNullVin'
}
其中returns出现以下错误:
Argument of type 'IVehicle' is not assignable to parameter of type 'IVehicleNonNullVin'.
Types of property 'vin' are incompatible.
Type 'string | null' is not assignable to type 'string'.
Type 'null' is not assignable to type 'string'.
即使我 阳性 属性 在这里也不可为空。
Q: 如何让TS相信现有模型符合代码流中基于类型检查的类型?
Demo in TS Playground
解决方法
作为变通方法,我可以转换类型(但这会忽略现有的类型安全):
needsVin(myVehicle as IVehicleNonNullVin);
或构建一个新模型(但这不能很好地扩展大量属性):
const nonNullVehicle: IVehicleNonNullVin = {
model: myVehicle.model,
vin: myVehicle.vin
}
needsVin(nonNullVehicle);
您可以使用 type predicate 来定义用户定义的类型保护,如下所示:
const isNonNullVin = (vehicle: IVehicle): vehicle is IVehicleNonNullVin =>{
return vehicle.vin !== null
}
if (!isNonNullVin(myVehicle)) {
throw new Error('null');
} else {
needsVin(myVehicle);
}
TypeScript will narrow that variable to that specific type if the original type is compatible.