What are interfaces in Go?
Tags: go, interfaces, learning, documentation
Published: 2023-08-10 20:50:36

(This is mainly a note to my future self, which may be useful for more people.)

I struggled so much to understand interfaces in Go and to develop a clear mental model of it. I have been using Go for only 50 days, but since I needed to understand as much as I could for a fast-paced project, I dived myself into the documentation (which is excellent) and all sources I could find.

The challenge here in this post is to try to explain what are interfaces in Go, without a specific order, ten (10) times, even if it sounds repetitive.

**1 - Runtime Polymorphism**

Not a particular definition, but runtime polymorphism can be achieved in Go using interfaces. 

Sources:

[Go Wikipedia](https://en.wikipedia.org/wiki/Go_(programming_language))
(See Interface System)

[Runtime polymorphism article](https://golangbyexample.com/runtime-polymorphism-go/)

Basically, it says that interfaces are a class of types and it makes an object which is of an interface type to be also of another type.

**2 - Interface type is a set of method signatures**

Source: 
[Tour of Go](https://go.dev/tour/methods/9)

This is simpler: You compose an interface type by providing one or more method signatures (not their implementation, which is the full code, but only the name, arguments taken and their types, and return types)

**3 - Interface type can hold any value that implements the methods defined in it**

Source: 
[Tour of Go](https://go.dev/tour/methods/9)

This part will need a recall of method definition but basically says that if there is an Example interface with Method1 and Method2 methods, any type that provides those methods will implement implicit the interface.

**4 - Any type works, not only functions but also common types. Example:**

```
type Abser interface {
	Abs() float64
}

type MyFloat float64

func (f MyFloat) Abs() float64 {
	if f < 0 {
		return float64(-f)
	}
	return float64(f)
}
```

Here, MyFloat satisfies Abser, since it has a receiver method with the same signature as the one declared in the interface.

**5 - Interfaces are implemented implicitly**

By simply implementing the interface methods, it is sufficient for implementing the interface.

**6 - Calling a method on an interface value executes the method of the same name on its underlying type**

Source: 
[Interface values - tour of Go](https://go.dev/tour/methods/11)

```
package main

import (
	"fmt"
	"math"
)

type I interface { // Interface I defines M() method
	M()
}

type T struct { // T struct contains S tring
	S string
}

// When calling M() on a *T struct, it will print the string it contains
func (t *T) M() { 
	fmt.Println(t.S)
}

type F float64

// When calling M() on a F type, it will print its value
func (f F) M() {
	fmt.Println(f)
}

// The magic here is that we are using the same method, M(), but it has different behavior based on the underlying type it references, thanks to interfaces.
func main() {
	var i I

	i = &T{"Hello"}
	describe(i)
	i.M()

	i = F(math.Pi)
	describe(i)
	i.M()
}

func describe(i I) {
	fmt.Printf("(%v, %T)\n", i, i)
}
```

**7 - Empty interface**

Sometimes is useful to provide an empty interface.

`interface{}`

It can hold values of any type because every type implements at least zero methods and can be used to handle values on unknown types.

**8 - "Duck-typing"**

"If it walks like a duck and it quacks like a duck, then it must be a duck"

This mostly refers to the fact that type conformance is not statically checked.

So, it is more correct to say that interfaces in Go are a form of structural typing.

**9 - Taking a look at the Effective Go definition**

Source:
[Interface and other types](https://go.dev/doc/effective_go#interfaces_and_types)

"Interfaces in Go provide a way to specify the behavior of an object: if something can do this, then it can be used here. We've seen a couple of simple examples already; custom printers can be implemented by a String method while Fprintf can generate output to anything with a Write method. Interfaces with only one or two methods are common in Go code and are usually given a name derived from the method, such as io.Writer for something that implements Write."

**10 - Interfaces in 42 words (generated by ChatGPT)**

"Go interfaces define a contract for methods that a type must implement. They enable polymorphism by allowing different types to be treated uniformly based on behavior rather than concrete type, fostering code reusability and abstraction in Go programs."

PS: Cover image generated by DreamStudio SDXL 1.0, prompt: "Highly interconnect digital interfaces in computer code, exchanging data and information in a futuristic manner"