Sobes.tech
Middle+

Why is embedding in the Go language not inheritance?

sobes.tech AI

Answer from AI

Embedding in Go allows one struct to use the fields and methods of another struct as if they were its own.

Key differences from inheritance:

  • Composition vs. Hierarchy: Embedding is a form of composition ("has-a"), where one struct has another. Inheritance (in classical OOP) is a form of hierarchy ("is-a"), where one class is a subclass of another.
  • Polymorphism: Go does not support subtype polymorphism in the traditional inheritance sense. Polymorphism in Go is implemented through interfaces.
  • Access: Embedding makes the fields and visible methods of the embedded struct directly accessible through the outer struct, but does not create a type hierarchy.
  • No overriding: There is no mechanism for direct "overriding" of base class methods. You can define a method with the same name in the outer struct, which will "shadow" the embedded method.

Example of embedding:

package main

import "fmt"

type Engine struct {
	Cylinders int
}

func (e Engine) Start() {
	fmt.Println("Engine started with", e.Cylinders, "cylinders")
}

type Car struct {
	Engine // Embedding Engine
	Brand  string
}

func main() {
	myCar := Car{
		Engine: Engine{Cylinders: 4},
		Brand:  "Toyota",
	}
	myCar.Start() // Access to Engine's Start method via Car
	fmt.Println("Car brand:", myCar.Brand)
	fmt.Println("Engine cylinders:", myCar.Cylinders) // Access to Engine's Cylinders field via Car
}

In this example, Car has Engine, but Car is not a subtype of Engine. We simply get convenient access to the fields and methods of Engine through the Car struct.