General interfaces

April 19, 2023

Today we’re venturing into generics territory.

General interfaces

In their most general form, an interface element may also be an arbitrary type term T, or a term of the form ~T specifying the underlying type T, or a union of terms t1|t<sub<>2|…|tn.

We haven’t actually learned about type terms yet–they’re coming in a few weeks. But for now, the TL;DR is that they let us specify a type by its name, rather than by its method(s).

We see some examples, just a bit later in the spec:

// An interface representing only the type int.
interface {
	int
}

// An interface representing all types with underlying type int.
interface {
	~int
}

We’ll talk in more detail about the ~ prefix shortly.

Quotes from The Go Programming Language Specification Version of December 15, 2022


Share this

Direct to your inbox, daily. I respect your privacy .

Unsure? Browse the archive .

Related Content


Type parameter restrictions

We’ll get to a full discussion of type parameters later on, but knowing at least what they look like is useful for the next section. So here’s an example, used in the definition of a generic function: func min[T ~int|~float64](x, y T) T { In this example, min[T ~int|~float64] represents the type parameter. With that in mind… General interfaces … The type T in a term of the form T or ~T cannot be a type parameter, and the type sets of all non-interface terms must be pairwise disjoint (the pairwise intersection of the type sets must be empty).


Interface type sets

With what we’ve learned so far about interfaces, we can now draw some general conclusions about the precise definitions of an interfce’s type set. The spec summarizes nicely. General interfaces … Together with method specifications, these elements enable the precise definition of an interface’s type set as follows: The type set of the empty interface is the set of all non-interface types. The type set of a non-empty interface is the intersection of the type sets of its interface elements.


Type switches with generics

More live coding today! Join me! And bring your questions. Type switches … A type parameter or a generic type may be used as a type in a case. If upon instantiation that type turns out to duplicate another entry in the switch, the first matching case is chosen. func f[P any](x any) int { switch x.(type) { case P: return 0 case string: return 1 case []P: return 2 case []byte: return 3 default: return 4 } } var v1 = f[string]("foo") // v1 == 0 var v2 = f[byte]([]byte{}) // v2 == 2 The example included is nice, because it shows two examples of the type parameter P being used: Both the first case (case P) and third (case []P) use the type parameter.

Get daily content like this in your inbox!

Subscribe