Go

How do you get and check the zero value of a type parameter T?

Question 121MediumGo 1.22 to 1.25

You cannot write return nil, and you cannot write T{} for an arbitrary T. nil is not valid for int, and composite literals need a core type. Use one of these idioms:

func First[T any](xs []T) (T, bool) {
    if len(xs) == 0 {
        var zero T // idiom 1
        return zero, false
    }
    return xs[0], true
}

func Default[T any]() T { return *new(T) } // idiom 2 (terse, allocation optimized away)

// Comparing with zero requires comparable
func IsZero[T comparable](v T) bool {
    var zero T
    return v == zero
}

// For any T (slices, maps, funcs), fall back to reflect
func IsZeroAny[T any](v T) bool {
    return reflect.ValueOf(&v).Elem().IsZero()
}

Gotchas:

  • IsZero[any](x) compiles, but it can panic if the dynamic type is not comparable (see the comparable question).
  • reflect.ValueOf(v) on a nil interface gives an invalid Value, which is why the example uses &v.
  • Returning (T, bool) or (T, error) is the idiomatic way to report "not found". It beats returning a sentinel zero.

More on Generics

All 36 Generics questions