By Dimitrios Arethas for the GopherCon 2019 Liveblog on July 26, 2019
Presenter: Ian Lance Taylor
Liveblogger: Dimitrios Arethas
Advantages and requirements for generics in Go.
In this talk, Ian outlined why the Go team feels like generics is a problem in need of tackling, what advantages they bring, and the requirements for what a generics implementation would be in Go.
Go released Nov 10 2009. Less than 24 hours later, the first comment about generics came through.
In three years of Go surveys, lack of generics has always been listed as one of the top 3 problems to fix in the language.
The definition of Generic programming for use in this talk: Generic programming enables the representation of functions and data structures in a generic form, with types factored out.
A simple example: reversing elements in a slice.
If you compare
ReverseStrings, the two
functions are exactly the same except for the type of the parameter.
What some people new to Go find surprising is that there is no way to
write a simple
Reverse function that works for a slice of any type.
So how would you do this in Go?
Interface types are a form of generic types. You can write a single function that works for different slice types by using an interface type, and defining a method on the slice types you want to pass in. That is how the standard library's sort.Sort function works.
But this approach falls short. With interfaces you have to write the methods yourself. And the methods you write are the same for each slice type. We just moved and condensed the duplicate code, which isn't what we want from generics.
A different way to use interfaces for generics is to have the language itself define methods for some kind of types.
Another approach is to write a generic
Reverse function using the reflect package but it is awkward to write and slow to run.
Or we could use code generation and write a generator that takes a type and generates a
Reverse function. But this adds another step to every package needs reverse, complicates the build, and makes fixing bugs difficult because you would need to regenerate it everywhere.
All these approaches are awkward enough that I think most people who have to reverse a slice in Go just write the function for the specific slice type that they need.
There must be a better way.
Back to our generics definition: The key thing is Generics factor out element types so we can write the reverse function once. This is what generics means for the purposes of this talk (the paraphrased Jazayeri definition in the slide). So for example, Ian doesn't mean templates in C++, which support quite a bit more than what is referenced.
Reverse function was described in detail these are a list of other functions that could be written generically.
It's not just functions that could be written generically, but data structures. Go already has two generic data structures built into the language: Slices and Maps.
IF we could write generic types, we could define new generic data structures like sets, self-balancing trees, multimaps, concurrent hash maps, etc.
These data structures should all be like
Reverse,` written once, put in a package and reused, with type checking at compile time.
So Generics can give us powerful building blocks to share code and build programs easily.
But every language change has a cost. With any change to the language, we need to talk about maximizing the benefit and minimizing the cost.
In Go, we’ve aimed to reduce complexity through independent, orthogonal language features that can be combined freely. We reduce complexity by making the individual features simple, and we maximize the benefit of the features by permitting their free combination. We want to do the same with generics.
Minimize new concepts
Complexity falls on writer of generic code, not user
Writer and user can work independently
Short build times, fast execution times
Preserve clarity and simplicity of Go.
The go team has been exploring this space for 10 years. Most of it is how to add generics that preserve clarity and simplicity.
Most important message of this talk:
Generics can bring a significant benefit to the language, but they are only worth doing if Go still feels like Go.
Ian then reviews last years contracts design and highlights the fact that some simplifications and feedback was taken into consideration for this year.
On the slides is a link to actual implementations using the current draft golang.org/cl/187317 [rec: 22:24]
Our goal is to arrive at a design that makes it possible to write the kinds of generic code I discused today without making the language too complex to use and without making it not feel like Go anymore.