Polymorphism in Go lang

Polymorphism in Go lang

ยท

3 min read

Table of contents

Polymorphism is the ability of an object or function to take on multiple forms. In the Go programming language, polymorphism is supported through the use of interfaces.

An interface in Go defines a set of methods that a type must implement to satisfy the interface. This means that any type that implements the methods defined in an interface is said to implement the interface.

For example, suppose we have an interface called Shape that defines the methods Area() and Perimeter() for calculating the area and perimeter of a shape. We could define the Shape interface like this:

type Shape interface {
    Area() float64
    Perimeter() float64
}

Now, any type that implements the Area() and Perimeter() methods can be said to implement the Shape interface. For example, we could define a Rectangle type that satisfies the Shape interface like this:

type Rectangle struct {
    width  float64
    height float64
}

func (r *Rectangle) Area() float64 {
    return r.width * r.height
}

func (r *Rectangle) Perimeter() float64 {
    return 2 * (r.width + r.height)
}

Here, the Rectangle type implements the Area() and Perimeter() methods, so it satisfies the Shape interface. This means that we can use a Rectangle value wherever a Shape is expected, and the appropriate method will be called automatically.

In this way, polymorphism in Go allows us to write code that can work with multiple types in a consistent manner, without needing to know the specific type of an object at compile time.

Example Code

package main

import "fmt"

type person struct{
    firstname string;
    lastname string
}

type human interface{
   talk()
}

func (p person) talk(){
  fmt.Println("My name is", p.firstname)
}
func main(){
    person1 := person{
        firstname: "Alfred",
        lastname: "Johnson-awah",
    }

    person1.talk()
}

In the code above we created a person struct which has the firstname and lastnameproperties. To showcase polymorphism, we created an interface with a function of talk. Lastly, we have implemented the talk function and attached it to a struct type of person . This means that any identifier of type person would always have a method talk and at the end of the day, we can boldly say that the identifier (person1 in our case) is of both person and human type, this is polymorphism.

You can still go ahead and add more complex code by implementing type assertion using a switch statement as seen below.

package main

import "fmt"

type person struct {
    firstname string
    lastname  string
}

type seniorMan struct {
    person
    hasACar bool
}

type human interface {
    talk()
}

func (p person) talk() {
    fmt.Println("My name is", p.firstname)
}

func (p seniorMan) talk() {
    fmt.Println("I am a person and senior man, see my ID", p, "and i have a car too", p.hasACar)
}

func resolveType(h human) {
    switch t := h.(type) {
    case person:
        fmt.Println("This is a normal person", t.firstname)
    case seniorMan:
        fmt.Println("This is a senior man, does this person have a car?", t.hasACar)

    }
}
func main() {
    person1 := person{
        firstname: "Alfred",
        lastname:  "Johnson-awah",
    }

    seniorMan1 := seniorMan{
        person: person{
            firstname: "Joe",
            lastname:  "Biden",
        },
        hasACar: true,
    }

    resolveType(seniorMan1)
    resolveType(person1)

    person1.talk()
}

Running this code on the console, your output should be like the below:

This is a senior man, does this person have a car? true
This is a normal person Alfred
My name is Alfred

The seniorMan struct type inherits properties of the person struct type with an additional property hasACar . The most important exerpt of this code is the resolveType function which uses a switch state to person type assertion on interfaces to find out their underlying types and execute the correct block of code.

Conclusion

In this blog post, we learnt about polymorphism and how it stems from interface implementation.