Go's Type System in One Sitting: Strings, Slices, Maps, and Implicit Interfaces
Go's type system is deliberately small, but the zero-value semantics, array-vs-slice distinction, and implicit interfaces are the three concepts that cause the most bugs and design friction for developers coming from Java, Python, or JavaScript. Getting them right early prevents entire categories of nil-pointer and copying mistakes.
Go's variable system starts with the full `var name type = value` declaration but quickly collapses into shorthand with type inference and the `:=` operator, which works only inside functions. Uninitialized variables don't stay null; they take a zero value — empty strings, 0 for ints, false for bools — a design choice that eliminates a class of nil-reference bugs before they start.
Arrays are fixed-length value types that copy on assignment, while slices are dynamic reference types backed by an array. The distinction matters for performance and mutation: passing an array copies the whole thing, but a slice shares the underlying data. Maps provide key-value lookups with a built-in comma-ok idiom for checking existence, sidestepping the zero-value ambiguity that plagues other languages.
Structs group fields into custom types, and interfaces tie everything together through implicit satisfaction — any type that implements the required methods automatically fulfills the contract without an `implements` keyword. This is Go's entire polymorphism story, and it's simpler than class hierarchies but demands a different mental model.
Zero values are Go's most underrated safety feature: they eliminate the billion-dollar null-reference mistake by making every type default to something useful rather than nothing.
The array-vs-slice distinction is where most newcomers leak memory or accidentally copy large data structures; slices are the default, and arrays exist mainly for low-level control.
Implicit interface satisfaction flips the dependency direction — packages define the interfaces they need, and implementations don't need to know about them, which keeps import graphs clean.
Go's type system is small enough to learn in an afternoon but subtle enough that the comma-ok map lookup and slice capacity behavior still surprise experienced developers in code review.
A brief exchange questions whether Go has an "automatic inheritance" problem, with a reply pushing back that Go lacks inheritance entirely. The third comment is just a reaction to the author learning Go.