A parent may have a child, a child may have a parent, but no more than one. Is it possible to make the difference using types ?
Here are the classes
class Child <T extends Parent | undefined> {
parent?: T
}
class Parent {
child?: Child<this>
change($: Child<undefined>): Child<undefined> | undefined {
const ans = this.child
const $$ = $ as unknown as Child<this>
$$.parent = this
this.child = $$
return ans as unknown as Child<undefined>
}
}
And usage:
const parent1 = new Parent()
const parent2 = new Parent()
parent1.change(new Child())
parent2.change(parent1.child)
Last line expectedly produces an error as parent1.child already has a parent!
There is a minor problem however: the extra variable $$ was used to avoid typecasting multiple times. We hope this is optimized by the transpiler/minifier used before shipping. Actually tsc does not optimize that code.