Goの定数は型のない状態で宣言できる。
const a = 1
こうしておくと、int
にもint64
にも代入できる、不思議な状態を作ることができ、便利である。
var i1 int = a
var i2 int64 = a
// コンパイルできる
一方で、型つきで定数を作ることもできる。
const b int = 1
この場合は型が固定されるので、int64
には代入ができない。
var i3 int = b
var i4 int64 = b // コンパイルエラー
iotaを使った連続宣言
iota
という定数のための記法がある。constでまとめて宣言する際に、自動でインクリメントした値を作ってくれて便利。
package main
import "fmt"
const (
aa int = iota
bb
cc
)
func main() {
fmt.Println(aa, bb, cc) // 0, 1, 2
}
このように型と値を省略する記法は特殊で、型の値と宣言を引き継ぐ。この場合aa, bb, cc
はすべてint
型で宣言されている。
var i5 int64 = cc // コンパイルエラーになる
iotaでなくても、こうすることができて、
const (
aa int = 1
bb
cc
)
この場合、aa,bb,cc全部がint型の1として宣言される。 (あまり意味がないのでiota以外ではこんな書き方はめったにしないが。)
iotaを使わずにまとめて定数宣言
iota記法を先に読んで、「あーなるほどそういうことね」と思ってはいけない。以下は間違いである。
package main
import "fmt"
const (
aa int = 0
bb = 1
cc = 2
)
func main() {
fmt.Println(aa, bb, cc) // 0, 1, 2
}
この場合、aaだけがint型として宣言されており、bbとccは型なしで宣言されていることになる。
aa~ccを全部int型で宣言するならば、こう書かないと駄目。
const (
aa int = 0
bb int = 1
cc int = 2
)
もしくは、これでもよい。
const aa, bb, cc int = 0, 1, 2
enumのようなものを作るときによく混乱するのでまとめた。