2015-12-16 06:03:43 +00:00
|
|
|
### 3.6.1. iota 常量生成器
|
|
|
|
|
2015-12-21 03:10:24 +00:00
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
常量聲明可以使用 iota 常量生成器, 用於生成一組相似的常量值, 但是不用每行都寫一遍. 在一個 const 聲明語句中, 在開始一行 iota 將會被置爲0, 然後在每一個有常量聲明的行加一.
|
2015-12-21 03:10:24 +00:00
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
下面是來自 time 包的例子, 它首先定義了Weekday命名類型, 然後爲一週的每天定義一個常量, 從週日0開始. 這種類型一般被稱爲枚舉類型.
|
2015-12-21 03:10:24 +00:00
|
|
|
|
|
|
|
```Go
|
|
|
|
type Weekday int
|
|
|
|
|
|
|
|
const (
|
|
|
|
Sunday Weekday = iota
|
|
|
|
Monday
|
|
|
|
Tuesday
|
|
|
|
Wednesday
|
|
|
|
Thursday
|
|
|
|
Friday
|
|
|
|
Saturday
|
|
|
|
)
|
|
|
|
```
|
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
週一將對應0, 週一爲1, 如此等等.
|
2015-12-21 03:10:24 +00:00
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
我們也可以在複雜的常量表達式中使用 iota, 下面是來自 net 包的例子, 用於給一個無符號整數的最低5bit的每個bit給定一個名字:
|
2015-12-21 03:10:24 +00:00
|
|
|
|
|
|
|
```Go
|
|
|
|
type Flags uint
|
|
|
|
|
|
|
|
const (
|
|
|
|
FlagUp Flags = 1 << iota // is up
|
|
|
|
FlagBroadcast // supports broadcast access capability
|
|
|
|
FlagLoopback // is a loopback interface
|
|
|
|
FlagPointToPoint // belongs to a point-to-point link
|
|
|
|
FlagMulticast // supports multicast access capability
|
|
|
|
)
|
|
|
|
```
|
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
隨着 iota 的遞增, 每個常量對應表達式 1 << iota, 是連續的2的冪, 分别對應一個bit位置. 使用這些常量可以測試, 設置, 或清除對應的bit位的值:
|
2015-12-21 03:10:24 +00:00
|
|
|
|
|
|
|
```Go
|
|
|
|
gopl.io/ch3/netflag
|
|
|
|
|
|
|
|
func IsUp(v Flags) bool { return v&FlagUp == FlagUp }
|
|
|
|
func TurnDown(v *Flags) { *v &^= FlagUp }
|
|
|
|
func SetBroadcast(v *Flags) { *v |= FlagBroadcast }
|
|
|
|
func IsCast(v Flags) bool { return v&(FlagBroadcast|FlagMulticast) != 0 }
|
|
|
|
|
|
|
|
unc main() {
|
|
|
|
var v Flags = FlagMulticast | FlagUp
|
|
|
|
fmt.Printf("%b %t\n", v, IsUp(v)) // "10001 true"
|
|
|
|
TurnDown(&v)
|
|
|
|
fmt.Printf("%b %t\n", v, IsUp(v)) // "10000 false"
|
|
|
|
SetBroadcast(&v)
|
|
|
|
fmt.Printf("%b %t\n", v, IsUp(v)) // "10010 false"
|
|
|
|
fmt.Printf("%b %t\n", v, IsCast(v)) // "10010 true"
|
|
|
|
}
|
|
|
|
```
|
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
下面是一個更複雜的例子, 每個常量都是1024的冪:
|
2015-12-21 03:10:24 +00:00
|
|
|
|
|
|
|
```Go
|
|
|
|
const (
|
|
|
|
_ = 1 << (10 * iota)
|
|
|
|
KiB // 1024
|
|
|
|
MiB // 1048576
|
|
|
|
GiB // 1073741824
|
|
|
|
TiB // 1099511627776 (exceeds 1 << 32)
|
|
|
|
PiB // 1125899906842624
|
|
|
|
EiB // 1152921504606846976
|
|
|
|
ZiB // 1180591620717411303424 (exceeds 1 << 64)
|
|
|
|
YiB // 1208925819614629174706176
|
|
|
|
)
|
|
|
|
```
|
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
iota 機製也有其局限性. 例如, 它併不能用於産生1000的冪(KB,MB,等等), 因爲併沒有計算冪的運算符.
|
2015-12-21 03:10:24 +00:00
|
|
|
|
2015-12-21 04:52:25 +00:00
|
|
|
**練習3.13:** 編寫KB,MB的常量聲明, 然後擴展到YB.
|
2015-12-21 03:10:24 +00:00
|
|
|
|
|
|
|
|