Skip to main content

Что такое zero value? Какие zero value имеют основные типы?

Zero value — это нулевое значение, которое Go автоматически присваивает переменной, если при её создании не было указано начальное значение.

var count int
var name string
var active bool

fmt.Println(count)  // 0
fmt.Println(name)   // ""
fmt.Println(active) // false

В Go переменная всегда содержит корректное значение своего типа — неинициализированных значений со случайными данными из памяти нет.

Zero values основных типов

ТипZero value
boolfalse
int, uint и другие целые числа0
float32, float640.0
complex64, complex1280 + 0i
string""
указатель *Tnil
слайс []Tnil
мапа map[K]Vnil
канал chan Tnil
функция funcnil
интерфейсnil
массив [N]Tмассив из zero values типа T
структураструктура, где каждое поле содержит свой zero value

Эти значения определены спецификацией Go.

Пример

type User struct {
	Name   string
	Age    int
	Active bool
	Tags   []string
}

var user User

fmt.Println(user.Name)   // ""
fmt.Println(user.Age)    // 0
fmt.Println(user.Active) // false
fmt.Println(user.Tags)   // []
fmt.Println(user.Tags == nil) // true

Каждое поле структуры получает zero value своего типа.

Особенности ссылочных типов

Слайс

Zero value слайса — nil. Его длина и ёмкость равны нулю, но с ним можно безопасно использовать range и append.

var numbers []int

fmt.Println(numbers == nil) // true
fmt.Println(len(numbers))   // 0

numbers = append(numbers, 10)
fmt.Println(numbers) // [10]

nil-слайс и созданный пустой слайс — не одно и то же:

var first []int
second := []int{}

fmt.Println(first == nil)  // true
fmt.Println(second == nil) // false

При этом оба имеют длину 0.

Мапа

Zero value мапы — nil.

Из nil-мапы можно читать:

var users map[string]int

fmt.Println(users["Alice"]) // 0

Если ключа нет, Go возвращает zero value типа значения мапы:

age, exists := users["Alice"]

fmt.Println(age)    // 0
fmt.Println(exists) // false

Но запись в nil-мапу вызывает panic:

var users map[string]int

// users["Alice"] = 30 // panic

Перед записью мапу нужно создать:

users = make(map[string]int)
users["Alice"] = 30

Указатель

Zero value указателя — nil.

var pointer *int

fmt.Println(pointer == nil) // true

Разыменование nil-указателя вызывает panic:

// fmt.Println(*pointer) // panic

Канал

Zero value канала — nil.

var ch chan int

Отправка данных в nil-канал и чтение из него блокируются, потому что такой канал не готов к передаче данных:

// ch <- 10
// value := <-ch

Рабочий канал создаётся через make:

ch := make(chan int)

Функция

Zero value функции — nil.

var handler func()

fmt.Println(handler == nil) // true

Вызов nil-функции приводит к panic:

// handler() // panic

Интерфейс

Zero value интерфейса — nil.

var err error

fmt.Println(err == nil) // true

Интерфейс равен nil, только когда внутри него нет ни конкретного типа, ни значения.

var pointer *MyError = nil
var err error = pointer

fmt.Println(err == nil) // false

Здесь интерфейс содержит тип *MyError, поэтому сам интерфейс не равен nil.

Массивы и структуры

В массиве каждый элемент получает zero value своего типа:

var numbers [3]int
var names [2]string

fmt.Println(numbers) // [0 0 0]
fmt.Println(names)   // ["" ""]

В структуре zero value получает каждое поле:

type Config struct {
	Port    int
	Address string
	Enabled bool
}

var config Config

// Config{
//     Port:    0,
//     Address: "",
//     Enabled: false,
// }

Итог

Zero value — это автоматически установленное начальное значение типа.

Основные правила:

bool       → false
numbers    → 0
string     → ""
*T         → nil
[]T        → nil
map[K]V    → nil
chan T     → nil
func       → nil
interface  → nil
array      → zero value каждого элемента
struct     → zero value каждого поля
Serzh AI Academy — Что такое zero value? Какие zero value имеют основные типы?