プログラムは通常、上から下へと順番に実行されますが、時には条件によって処理を変えたり、同じ処理を繰り返したりする必要があります。Go言語では、そのような制御を行うために if
文、for
文、switch
文が用意されています。これらを使いこなして、より柔軟なプログラムを作成しましょう! 💪
if文:条件による分岐 🤔
if
文は、指定した条件が真 (true
) か偽 (false
) かによって、実行する処理を分岐させます。
基本的なif文
条件式が true
の場合に、続くブロック { }
内の処理を実行します。
package main
import "fmt"
func main() {
score := 85
if score > 80 {
fmt.Println("素晴らしい!合格です! 🎉") // score > 80 が true なので実行される
}
}
if-else文
条件式が true
の場合と false
の場合で、それぞれ異なる処理を実行します。
package main
import "fmt"
func main() {
age := 18
if age >= 20 {
fmt.Println("成人です。")
} else {
fmt.Println("未成年です。") // age >= 20 が false なのでこちらが実行される
}
}
if-else if-else文
複数の条件で分岐させたい場合に使用します。
package main
import "fmt"
func main() {
score := 75
if score >= 90 {
fmt.Println("優")
} else if score >= 80 {
fmt.Println("良")
} else if score >= 70 {
fmt.Println("可") // score >= 70 が true なのでこちらが実行される
} else {
fmt.Println("不可")
}
}
簡易ステートメント付きif文
Goの特徴的な書き方として、if
の条件式の前に簡単なステートメント(通常は変数宣言と初期化)を書くことができます。ここで宣言された変数のスコープ(有効範囲)は、if
文とその else if
/ else
ブロック内に限定されます。これはコードを簡潔にし、変数の影響範囲を狭めるのに役立ちます。✅
package main
import (
"fmt"
"math/rand"
"time"
)
func main() {
// Go 1.20 より前では Seed の設定が推奨されていました
// rand.Seed(time.Now().UnixNano())
// 簡易ステートメントで乱数を生成し、その値で分岐
if n := rand.Intn(10); n > 5 {
fmt.Printf("%d は 5 より大きい\n", n)
// 変数 n はこの if ブロック内でのみ有効
} else {
fmt.Printf("%d は 5 以下\n", n)
// 変数 n はこの else ブロック内でのみ有効
}
// fmt.Println(n) // ここでは n は使えない (スコープ外)
}
if
(および関連する else if
/else
) ブロック内に限定されます。for文:繰り返し処理 🔁
Go言語の繰り返し処理は for
文のみで表現されます。他の言語にある while
や do-while
に相当する構文はありませんが、for
文の柔軟な書き方でそれらを表現できます。
基本形 (C言語スタイル)
初期化ステートメント、条件式、後処理ステートメントを指定します。
package main
import "fmt"
func main() {
sum := 0
// 1から10までの合計を計算
for i := 1; i <= 10; i++ { // 初期化; 条件; 後処理
sum += i
}
fmt.Println("合計:", sum) // 合計: 55
}
条件のみ (whileスタイル)
条件式のみを指定すると、その条件が true
である間、繰り返し処理を実行します。
package main
import "fmt"
func main() {
n := 1
// nが100未満の間、2倍し続ける
for n < 100 {
n *= 2
}
fmt.Println("結果:", n) // 結果: 128
}
無限ループ
条件式を省略すると無限ループになります。ループを抜けるには break
文を使用します。
package main
import (
"fmt"
"time"
)
func main() {
count := 0
for { // 無限ループ
fmt.Println("ループ中...")
time.Sleep(500 * time.Millisecond)
count++
if count >= 3 {
fmt.Println("ループを抜けます。")
break // countが3以上になったらループを終了
}
}
}
ループ内の特定の回の残りの処理をスキップして次のイテレーションに進むには continue
文を使用します。
for range ループ ✨
スライス、配列、マップ、文字列、チャンネルなど、反復可能なデータ構造の要素を順番に取り出すのに便利です。
package main
import "fmt"
func main() {
// スライスの例
nums := []int{10, 20, 30}
sum := 0
// インデックス(i)と値(num)を取得
for i, num := range nums {
fmt.Printf("インデックス: %d, 値: %d\n", i, num)
sum += num
}
fmt.Println("スライスの合計:", sum)
// 値だけ必要な場合 (インデックスを無視)
sum = 0
for _, num := range nums { // インデックスを _ で破棄
sum += num
}
fmt.Println("スライスの合計 (値のみ):", sum)
// マップの例
kvs := map[string]string{"a": "Apple", "b": "Banana"}
// キー(k)と値(v)を取得
for k, v := range kvs {
fmt.Printf("%s -> %s\n", k, v)
}
// キーだけ必要な場合
for k := range kvs {
fmt.Println("キー:", k)
}
// 文字列の例 (rune単位で反復)
for i, r := range "Go言語" {
fmt.Printf("%d: %c\n", i, r) // iはバイト単位のインデックス, rはrune(文字)
}
}
for range
ループ内で取得した変数はループ全体で同じメモリアドレスを指していましたが、Go 1.22からは各イテレーションで新しい変数が作られるように挙動が変更されました。これにより、ループ変数を使ったゴルーチンなどでの意図しないバグが起こりにくくなりました。初学者の段階では大きな影響はないかもしれませんが、知っておくと良いでしょう。switch文:多岐分岐 🚦
switch
文は、ある式の値に基づいて、複数の処理経路から一つを選んで実行します。if-else if
を重ねるよりも簡潔に書ける場合があります。Goの switch
は、一致した case
の処理が終わると自動的に switch
文を抜けます(暗黙の break
)。
基本的なswitch文
package main
import "fmt"
func main() {
signal := "red"
switch signal {
case "red":
fmt.Println("止まれ 🚦")
case "yellow":
fmt.Println("注意 ⚠️")
case "blue", "green": // 複数の値をまとめることも可能
fmt.Println("進め 👍")
default: // どの case にも一致しない場合
fmt.Println("不明な信号")
}
}
fallthrough
Goでは通常、case
の終わりに暗黙的な break
がありますが、意図的に次の case
の処理も実行したい場合は fallthrough
キーワードを使用します。ただし、fallthrough
の使用はコードを読みにくくすることがあるため、慎重に使いましょう。
package main
import "fmt"
func main() {
num := 2
switch num {
case 1:
fmt.Println("1")
fallthrough // 次のcaseも実行
case 2:
fmt.Println("2") // ここが実行される
fallthrough // さらに次のcaseも実行
case 3:
fmt.Println("3") // ここも実行される
default:
fmt.Println("default")
}
// 出力:
// 2
// 3
}
式なしswitch (switch true)
switch
の後に式を書かない場合、switch true
と同じ意味になり、各 case
に書かれた条件式を上から順に評価し、最初に true
になった case
の処理を実行します。これは複雑な if-else if-else
文をよりきれいに書く方法として使えます。
package main
import "fmt"
func main() {
score := 88
switch { // 式を省略 (switch true と同じ)
case score >= 90:
fmt.Println("優")
case score >= 80:
fmt.Println("良") // ここが true になるので実行される
case score >= 70:
fmt.Println("可")
default:
fmt.Println("不可")
}
}
switch
は、条件分岐が複数ある場合にコードを読みやすくするのに役立ちます。👍
コメント