Какие типы в Go являются сравнимыми (comparable) и каковы правила сравнения?

Ответ

Сравнимые типы (comparable) — это типы, значения которых можно использовать в операциях сравнения == и !=.

Сравнимые типы:

  1. Базовые типы: bool, все числовые типы (int, float64 и т.д.), string.
  2. Указатели: Два указателя равны, если они указывают на одну и ту же переменную или оба равны nil.
  3. Каналы: Два канала равны, если они были созданы одним и тем же вызовом make или оба равны nil.
  4. Интерфейсы: Два интерфейса равны, если их динамические типы и динамические значения равны, или если оба равны nil.
  5. Массивы: Два массива сравнимы, если их типы элементов сравнимы. Они равны, если все их соответствующие элементы равны.
  6. Структуры: Две структуры сравнимы, если все их поля сравнимы. Они равны, если все их соответствующие поля равны.

Несравнимые типы:

  • Срезы ([]T)
  • Карты (map[K]V)
  • Функции (func())

Эти типы можно сравнивать только с nil.

Пример:

// Массивы сравнимы, так как их элементы (int) сравнимы
a1 := [2]int{1, 2}
a2 := [2]int{1, 2}
fmt.Println(a1 == a2) // true

// Срезы несравнимы между собой
b1 := []int{1, 2}
// b2 := []int{1, 2}
// fmt.Println(b1 == b2) // Ошибка компиляции: invalid operation: b1 == b2 (slice can only be compared to nil)

// Но срез можно сравнить с nil
var b2 []int
fmt.Println(b1 == nil) // false
fmt.Println(b2 == nil) // true