Enumy, zkráceně „enumerations“, jsou způsob, jak definovat pevný seznam souvisejících hodnot. I když Go nemá vestavěný typ enum jako některé jiné programovací jazyky (např. Java nebo C#), nabízí silný mechanismus pomocí konstant a klíčového slova iota.
Co je iota?
iota je předdeklarovaný identifikátor v Go, který se primárně používá k usnadnění vytváření číslovaných konstant. Začíná na 0 pro první konstantu v bloku const a zvyšuje se o 1 pro každou následující konstantu. Díky tomu je ideálním nástrojem pro tvorbu enumů, protože eliminuje nutnost ručně přiřazovat hodnoty jednotlivým konstantám.
Základní příklad enumů v Go
Zde je příklad, jak definovat dny v týdnu bez použití iota:
const (
Sunday  = 0
Monday  = 1
Tuesday = 2
Wednesday = 3
Thursday = 4
Friday  = 5
Saturday = 6
)
S iota lze toto zjednodušit:
const (
Sunday = iota
Monday
Tuesday
Wednesday
Thursday
Friday
Saturday
)
Klíčové slovo iota automaticky přiřadí hodnoty 0 až 6 od Sunday do Saturday, což činí kód čistší a snadněji udržovatelný.
Výhody použití iota
Není potřeba ručně přiřazovat hodnoty
Kód je snadno udržovatelný
Můžete definovat vlastní hodnoty založené na iota
Pokročilé příklady
Přeskakování hodnot
Občas je potřeba některé hodnoty vynechat. To lze dosáhnout pomocí prázdného identifikátoru _:
const (
  Red = iota
  _   // Přeskočíme 1
  Blue
  Green
)

  // Red = 0, Blue = 2, Green = 3
Zahájení od jiného posunu
Můžete nastavit počáteční posun pro váš enum pomocí aritmetiky s iota:
const (
  Bronze = iota + 1  // Začne od 1
  Silver
  Gold
)

  // Bronze = 1, Silver = 2, Gold = 3
Použití iota pro bitové masky
iota je také užitečné pro definování bitových masek:
const (
  Read    = 1 << iota // 1 << 0 = 1
  Write               // 1 << 1 = 2
  Execute             // 1 << 2 = 4
)

  // Read = 1, Write = 2, Execute = 4
Toto je zvláště užitečné při práci s oprávněními nebo příznaky.
Seskupování konstant
Můžete znovu použít iota v oddělených blocích const:
const (
  Circle = iota
  Square
  Triangle
)

  const (
      Low = iota + 1 // Začíná od 1 v tomto bloku
      Medium
      High
  )

  // Circle = 0, Square = 1, Triangle = 2
  // Low = 1, Medium = 2, High = 3
Praktické použití
Enumy se často používají k reprezentaci souvisejících hodnot. Podívejme se na praktičtější příklad: enum pro úrovně logování.
package main

  import "fmt"

  const (
      Debug = iota
      Info
      Warning
      Error
      Critical
  )

  func Log(level int, message string) {
      switch level {
      case Debug:
          fmt.Println("[DEBUG]", message)
      case Info:
          fmt.Println("[INFO]", message)
      case Warning:
          fmt.Println("[WARNING]", message)
      case Error:
          fmt.Println("[ERROR]", message)
      case Critical:
          fmt.Println("[CRITICAL]", message)
      default:
          fmt.Println("[UNKNOWN]", message)
      }
  }

  func main() {
      Log(Info, "Aplikace byla spuštěna.") // [INFO] Aplikace byla spuštěna
      Log(Error, "Došlo k chybě.") // [ERROR] Došlo k chybě.
  }
V tomto příkladu iota pomáhá definovat úrovně logování a příkaz switch mapuje úrovně na odpovídající zprávy.
Tipy pro použití enumů v Go
Používejte popisné názvy: Pojmenujte své konstanty tak, aby zlepšily čitelnost kódu
Validujte vstupy: Enumy jsou obvykle celá čísla, takže validujte vstupy, aby odpovídaly očekávanému rozsahu
Používejte textové reprezentace: Implementujte metodu String() pro lepší logování a ladění
func (level int) String() string {
  switch level {
  case Debug:
      return "Debug"
  case Info:
      return "Info"
  case Warning:
      return "Warning"
  case Error:
      return "Error"
  case Critical:
      return "Critical"
  default:
      return "Unknown"
  }
}