Skip to content

Polymorphism not working correctly with union types #42032

Closed
@hgl

Description

@hgl

TypeScript Version: 4.1.2

Search Terms: polymorphism union

Code

abstract class Person {
  name: [string, string]

  constructor(p: Person)
  constructor(p: {name: string})
  constructor(p: Person | {name: string}) {
    if (p instanceof Person) {
      this.name = p.name
    } else {
      let parts = p.name.split(/\s+/)
      this.name = [parts[0] || "", parts[1] || ""]
    }
  }
}

class SadPerson extends Person {
  sadness: number
  constructor(p: {name: string}, sadness: number) {
    super(p)
    this.sadness = sadness
  }
  cry() {
    console.log("crying")
  }
}

class HappyPerson extends Person {
  happiness: number
  constructor(p: SadPerson)
  constructor(p: {name: string}, happiness: number)
  constructor(p: SadPerson | {name: string}, happiness?: number) {
    super(p)
    this.happiness = p instanceof SadPerson ? -p.sadness : happiness!
  }
  smile() {
    console.log("smiling")
  }
}

Expected behavior:
super(p) in HappyPerson's constructor should compile successfully.
Actual behavior:
ts complains "No overload matches this call."

Though it can be fixed by replacing super(p) with

if (p instanceof Person) {
  super(p)
} else {
  super(p)
}

But this feels strictly redundant.

I'm pretty sure there is already some ticket that described this, but I couldn't find it using the search term. Hope someone could link to it and I will close this one as a duplicate.

Playground Link:
https://www.typescriptlang.org/play?#code/IYIwzgLgTsDGEAJYBthjAgCgUymA9gHYIDeAUAgocALbYBcCA2pFAJaEDmANAqx5wC6ZCkiKsArvHxQAFAAdGOPEQCUo2OOhSIMhYxLU6jflwC+6ypsKTpcxVlwFiAH1JGGfaAIulRlNgAzBAUEDkhgQlhsfGDlZ1U-SmSECAALNjAAOg8EAF4EeRzabH8EMwRsZDBsJJSEZGxEeWAoCAwCoo8ssHlkNghZAHoAHTAAaiHLevTM4rp85ha2sCYABkEEFzcAIh3eZfamAEZN7YQ94RSzURubshQ0DABlYAATeKJKgA8IbEI3hhPsRyJQwO9CNh0IxCBIaCBcBotFAdHoHIYSiZvOZeOC3pDoVQ4QioIlQckwBJ5LgFNNKLNsniCR0+BCoWBbhooABPWRksrWAiNLLIfCcWQ7WA8gQ7aZ3ESPdAIAASwHk8m5wJ+fwBQKcX3JaTV8g47JhxMRVmRqPsjFeH31hGmgu0dn07kxXnYOIQRvVpsJsPhuGd1rdDntWrcGOMXp8vD9JuZAH5zcHSXUwVSafI6akMtlEwGWfIwjYIJForEEJHHQhkwgALRFJnshCMIvMgCEnLBNDYjT5mbENnwwtF4p2YH7-S4ss5ZiAA

Related Issues:

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions