Ответ
Нулевой (nil) слайс — это слайс, который не указывает ни на какой базовый массив. Он является значением по умолчанию для типа []T
.
var s []int // s является nil-слайсом
Несмотря на то, что он nil
, он безопасен и полезен для многих операций.
Допустимые операции
- Получение длины и ёмкости:
len(s)
иcap(s)
для nil-слайса всегда возвращают0
. - Добавление элементов: Операция
append
прекрасно работает с nil-слайсом. При первом вызовеappend
будет выделен новый базовый массив, и слайс перестанет бытьnil
.var s []int s = append(s, 1) // Работает корректно
- Использование в цикле
for range
: Цикл по nil-слайсу просто не выполнит ни одной итерации, не вызывая ошибок.for _, v := range s { // Безопасно, цикл не начнется // ... }
- Сравнение с
nil
:s == nil
вернетtrue
.
Недопустимые операции
- Доступ по индексу: Попытка получить или изменить элемент по индексу (
s[0] = 1
или_ = s[0]
) вызовет паникуpanic: runtime error: index out of range
, так как длина слайса равна нулю.
Отличие от пустого (не-nil) слайса
Важно отличать nil-слайс от пустого слайса, который указывает на существующий (хоть и пустой) массив.
var nilSlice []int // nilSlice == nil -> true
emptySlice := make([]int, 0) // emptySlice == nil -> false
emptySlice2 := []int{} // emptySlice2 == nil -> false
Ключевое преимущество: В большинстве случаев nil-слайс ведет себя так же, как и пустой (в len
, cap
, append
, range
). Поэтому в Go идиоматично не инициализировать пустые слайсы специально (make([]T, 0)
), а просто объявлять их через var
, что делает код чище и не требует лишних аллокаций.