Це правда, що наведені вище приклади використання const
та iota
є найбільш ідіоматичними способами представлення примітивних перерахунків у Go. Але що робити, якщо ви шукаєте спосіб створити більш повнофункціональний перелік, схожий на тип, який ви бачите на іншій мові, як Java або Python?
Дуже простий спосіб створити об’єкт, який починає виглядати і відчувати себе струнним перерахунком в Python, це:
package main
import (
"fmt"
)
var Colors = newColorRegistry()
func newColorRegistry() *colorRegistry {
return &colorRegistry{
Red: "red",
Green: "green",
Blue: "blue",
}
}
type colorRegistry struct {
Red string
Green string
Blue string
}
func main() {
fmt.Println(Colors.Red)
}
Припустимо, ви також хотіли деякі корисні методи, як-от Colors.List()
і Colors.Parse("red")
. А ваші кольори були складнішими і потребували структури. Тоді ви можете зробити щось подібне:
package main
import (
"errors"
"fmt"
)
var Colors = newColorRegistry()
type Color struct {
StringRepresentation string
Hex string
}
func (c *Color) String() string {
return c.StringRepresentation
}
func newColorRegistry() *colorRegistry {
red := &Color{"red", "F00"}
green := &Color{"green", "0F0"}
blue := &Color{"blue", "00F"}
return &colorRegistry{
Red: red,
Green: green,
Blue: blue,
colors: []*Color{red, green, blue},
}
}
type colorRegistry struct {
Red *Color
Green *Color
Blue *Color
colors []*Color
}
func (c *colorRegistry) List() []*Color {
return c.colors
}
func (c *colorRegistry) Parse(s string) (*Color, error) {
for _, color := range c.List() {
if color.String() == s {
return color, nil
}
}
return nil, errors.New("couldn't find it")
}
func main() {
fmt.Printf("%s\n", Colors.List())
}
У той момент впевнений, що він працює, але вам може не сподобатися, як вам потрібно повторювати кольори. Якщо в цей момент ви хочете усунути це, ви можете використати теги на вашій структурі і зробити деякі фантазії, що відображають її настройку, але, сподіваємось, цього достатньо, щоб охопити більшість людей.