Updated new() function
In the Go language update 1.26 there is an update to new() function. The function can now take an expression as an
argument 1. This seemingly small change allows us to simplify lots of boilerplate code that we had to write up
until now.
Previously we had to come up with utility functions that return a pointer to a given type like the ones below. We had to write either specific ones with a given type or use generics.
func getPtrToBool(b bool) *bool {
val := b
return &val
}
func getPtr[T any](t T) *T {
return &t
}
p1 := getPtrToBool(true)
p2 := getPtr[int64](42)
fmt.Println(p1, p2)
// outputs: 0x13ed1724c0d 0x13ed1724c10
Previously, new() only accepted a type (new(int)), which always gave you a pointer to the zero value of that type.
You then had to set the value in a separate step. Now you can pass an expression as a function argument.
Examples:
- Boolean
new(true) - String
new("Hello, Go 1.26") - Integer
new(42) - Float
new(3.14159) - Complex number
new(1 + 2i) - Slice literal
new([]int{1, 2, 3}) - Map literal
new(map[string]int{"a": 1}) - Function result
new(time.Now())
This is especially helpful when working with optional values in JSON, protocol buffers, or APIs where fields may or may not be present. It is also super useful in unit tests.
type Person struct {
Name string
Age *int
}
p3 := Person{Name: "Alice", Age: new(30)}
fmt.Println(p3)
// output: {Alice 0x3b6ce091ec18}
In real-world backend systems, especially when dealing with JSON, protobuf, and optional fields, this significantly
improves clearness, pointer ergonomics, and code readability. The behavior is exactly equivalent to allocating a
zero-value pointer and then assigning it’s just expressed more concisely. The release 1.26 maintains the Go promise of
compatibility. Go programs continue to compile and run as before.
The new(expr) is still:
- types are inferred from untyped constants passed (
intis inferred from10) - you cannot call
new(nil)because nil does not have a concrete type for the compiler to allocate - Heap-allocates the value (same as before)
- Returns a pointer
*Tto the newly allocated variable - Is fully backward compatible — existing code using
new(SomeType)continues to work unchanged