Рассмотрим эту ситуацию (фиктивный пример):
class Farmer<A extends Animal<Farmer<A>>>
{
public animal: A;
constructor() {
let a = new Animal(this);
// ...
}
}
class Animal<F extends Farmer<Animal<F>>>
{
public farmer: F;
constructor(f: F) {
this.farmer = f;
}
}
Кто-нибудь может объяснить, почему в конструкторе Farmer
(где я передаю аргумент this
new Animal
) приведенный выше код вызывает эту ошибку?
TS2345: Argument of type 'this' is not assignable to parameter of type 'Farmer<Animal<this>>'.
Type 'Farmer<A>' is not assignable to type 'Farmer<Animal<this>>'.
Type 'A' is not assignable to type 'Animal<this>'.
Type 'Animal<Farmer<A>>' is not assignable to type 'Animal<this>'.
Type 'Farmer<A>' is not assignable to type 'this'.
Следующее решение вопроса:
class Farmer<A extends Animal<Farmer<A>>>
{
public animal: A;
constructor() {
let a = new Animal(this as Farmer<A>); // works fine
}
}
Или как альтернатива:
class Farmer<A extends Animal<Farmer<A>>>
{
public animal: A;
constructor() {
let a = new Animal<Farmer<A>>(this); // works fine
}
}
Более странным для меня является следующее:
class Farmer<A extends Animal<Farmer<A>>>
{
// public animal: A; // removed this line
constructor() {
let a = new Animal(this); // now this one works fine too
}
}
Хотя первые два решения достаточно ясны, последнее вызывает у меня больше сомнений.
Кто-нибудь может объяснить, что случилось?
Редактировать
Следующее хорошо (рассмотрим необязательный параметр в конструкторе Animal
):
class Farmer<A extends Animal<Farmer<A>>>
{
public animal: A;
constructor() {
let a = new Animal();
a.farmer = this; // works fine
}
}
И здесь я не вижу никакой разницы в типах по сравнению с первым случаем.