typescript的基本结构,TypeScript构造函数

i tried to create a class with two constructors and find out that TypeScript are not allowing that, but it allow overloading of constructor, well I tried it to and get an error :

Build: Overload signature is not compatible with function implementation.

My code:

interface IShoppingListItem {

name: string;

amount: number;

}

export class ShoppingListItem implements IShoppingListItem{

name: string;

amount: number;

constructor(item: IShoppingListItem);

constructor(name: string, amount: number) {

this.name = name;

this.amount = amount;

}

copy() {

//return new this.constructor(this);

}

}

I have two question, first one, why can't I overloading the constructor, I guess I'm doing something wrong.

But my second question, and more interacting is, i know i constructor that get optional values. Can I, (not with the code inside the method!), create a condition on my constructor that can verify that one of the two given value have to exist, while in the signature boot are optional, like so:

constructor(item?: IShoppingListItem, name?: string, amount?: number) {

//make a condition that item or name and amount must exist

this.name = name;

this.amount = amount;

}

Thanks.

解决方案

In Typescript, function overloading is nothing more than defining additional call signatures for a single function body. And since there is only one function body, all overload signatures must be compatible with that initial function declaration. Type- and value-checking of arguments are to be done manually.

In your case, it's a bit tricky, as interface definitions are lost upon compilation, therefore you'll have no clean approach to check if the passed argument is an implementation of the given interface. Luckily, it's an "object or string" check for your first parameter, and an "exists or not" for the second, so checking whether or not the interface is implemented is unnecessary:

export class ShoppingListItem implements IShoppingListItem {

// 2 overload signatures from which you can choose on the invocation side

constructor(item: IShoppingListItem);

constructor(name: string, amount: number);

// the function declaration itself, compatible with both of the above overloads

// (in VS, IntelliSense will not offer this version for autocompletion)

constructor(nameOrItem: string | IShoppingListItem, amount?: number) {

if (typeof nameOrItem === "object") {

// the first argument is an object, due to overload signature,

// it is safe to assume it is of type IShoppingListItem

// ...

} else if (typeof nameOrItem === "string" && typeof amount === "number") {

this.name = nameOrItem;

this.amount = amount;

}

}

}

Here, both overloads are compatible with the initial signature. Parameter names do not matter, only their respective types and ordering (as well as optionality).

The TypeScript compiler is aware of typeof and instanceof checks, which results in your variable being treated as the correct type inside a conditional block as such. This is called a type guard.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值