Generics, introduced in Go 1.18, allow developers to write more flexible and reusable code. This feature enables the creation of functions and types that can work with multiple data types while maintaining type safety.
Generics provide a way to write code that operates on different types without sacrificing type safety. They are particularly useful when creating data structures and algorithms that can work with various data types.
To define a generic function or type, use square brackets to specify type parameters:
func PrintSlice[T any](s []T) {
for _, v := range s {
fmt.Println(v)
}
}
In this example, T
is a type parameter that can represent any type.
func Max[T constraints.Ordered](a, b T) T {
if a > b {
return a
}
return b
}
This function works with any type that satisfies the Ordered
constraint, such as integers or floats.
Go generics use type constraints to specify which types can be used with a generic function or type. The any
constraint allows any type, while more specific constraints can be defined using interfaces.
type Number interface {
int | float64
}
func Sum[T Number](numbers []T) T {
var sum T
for _, n := range numbers {
sum += n
}
return sum
}
This Sum
function works with slices of integers or float64 values.
To fully understand and utilize Go generics, it's helpful to be familiar with these related concepts:
By mastering Go generics, you'll be able to write more flexible and reusable code, improving your overall productivity and code quality.