枚举的本质是什么,我们天天写代码用枚举,那啥是枚举啊。wiki上是这样说的在计算机编程中,枚举类型(也在R编程语言中称为枚举、枚举或因子,在统计学中称为分类变量)是一种数据类型,由一组称为该类型的元素、成员、枚举或枚举数的命名值组成。枚举器名称通常是在语言中表现为常量的标识符。枚举类型可以看作是单元类型的退化标记联合。已声明为具有枚举类型的变量可以分配任何枚举数作为值。换句话说,枚举类型具有彼此不同的值,可以比较和赋值,但程序员没有指定在计算机内存中具有任何特定的具体表示;编译器和解释器可以任意表示它们。用人说话就是枚举是强类型编程语言中的一种类型,由一组名称和值组合而成。通常用作编程语言中常量的标识符。这没有什么不妥,这正是我们使用它的方式。比如我上学的时候经常写c的小玩具代码。c标准中提供了enum关键字,写起来比较直白。使用时类似于struct。它需要像enumweek这样写。c中默认的枚举值是从0开始的int类型,其实在c中枚举就是作为int类型使用的。#includeenumweek{Mon,Tue,Wed,Thur,Fri,Sat,Sun};intmain(){enumweekday;//需要加上enum关键字day=Wed;printf("%d",day);//Output2inti;for(i=Mon;i<=Sun;i++){//可以直接将枚举类型赋值给int类型printf("%d",i);//Output0,1,2,3,4,5,6}return0;}上面的例子没问题,初始化的时候,枚举值默认,编译器会从0开始赋值,比如上面的Mon=0,Tue=1...,但我也想自己赋值,而不是编译器默认的赋值方式。具体怎么写,看下面的例子:#includeenumday{sunday=1,monday,tuesday=5,wednesday,thursday=10,friday,saturday};intmain(){printf("%d%d%d%d%d%d%d",sunday,monday,tuesday,wednesday,thursday,friday,saturday);//输出1256101112return0;}也就是说可以给一个名字赋值在枚举中的任何顺序。所有未分配的名称的值都将作为先前名称的值递增1。其实定义几个常量,用宏是不是更好,比如写#definesunday0#definemonday1#definetuesday2但是老师说了,尽量不要用宏,不是说宏不好,宏也好,编译器替换,没有运行时,多快,但是有几个问题:1)宏没有作用域2)枚举是类型安全的。有点远。现在回头看看Go中的枚举是怎样的。写。当然,它也很简单。官方教我们这样写:typeByteSizefloat64const(_=iotaKByteSize=1<<(10*iota)MBGB)在Go中更简洁,直接去掉了enum关键字。其实从Go的角度来看,enum不就是一个常量吗?为什么你有这么多语法糖?Go提供了一个关键字iota来增加常量。它还支持手动分配。结合iota和手动赋值可以达到类似c中const的效果。(A0=iotaA1=iotaA2=iota)fmt.Println(A0,A1,A2)//“012”可以简写为const(A0=iotaA1A2)也可以从1开始const(A1=iota+1A2A3)fmt.Println(A1,A2,A3)//"123"orskipacertainvalueconst(C1=iota+1_C3C4)fmt.Println(C1,C3,C4)//"134"看到这里你可能会有疑问,这里的枚举实际上是一个常量吗?那如何写一个string类型的枚举呢?你可能会说,当然,使用字符串常量。但是那只是一个字符串常量,没有枚举的性质。我可能想要的是一个字符串到值的枚举类型。反复思考,看看我的写法是否OK:第一步:新建一个int类型第二步:用iota表示值第三步:给这个新类型一个String方法typeDirectionintconst(NorthDirection=iotaEastSouthWest)func(dDirection)String()string{return[...]string{"North","East","South","West"}[d]}当使用vardDirection=Northfmt.Print(d)switchd{caseNorth:fmt.println("goesup.")caseSouth:fmt.Println("goesdown.")default:fmt.Println("staysput.")}当然还有另一种方式,比较stupidtypeweekdaystringfunc(wweekday)isWeekday()weekday{returnw}typeWeekdayinterface{isWeekday()weekday}const(Monday=weekday("Monday")Tuesday=weekday("Tuesday")Wendsday=weekday("Wendsday")Thursday=weekday("Thursday")Friday=weekday("Friday")周六=weekday("Saturday")Sunday=weekday("Sunday"))//使用funcmain(){vard1=weekday.Mondayvard2=weekday.Tuesdayfmt.Println(d1,d2,d1==d2,d1==weekday.Monday)}如果用struct表示枚举,那么其实可以用反射,比如写成follows:import("反射t")typeweekdaystruct{Monday,Tuesday,Wendsday,Thursday,Friday,Saturday,Sundayint}func(cweekday)Get(idstring)int{vo:=reflect.ValueOf(c)typeVo:=vo.Type()fori:=0;i