[Golang]配列(array)をシャッフルするには?

Go

どうも、ちょげ(@chogetarou)です。

配列(array)の要素をシャッフルしてランダムに並び替える方法を紹介します。

スポンサーリンク

方法

配列(array)の要素をシャッフルしてランダムに並び替える方法は、2つあります。

rand.Shuffle()

ひとつは、「rand.Shuffle()」を使う方法です。

まず、「math/rand」をインポートします。

import "math/rand"

次に、randからShuffle()を呼び出します。

Shuffle()の第1引数に配列の要素数、第2引数に整数の2つの引数を持つ関数を指定します。

そして、関数の処理で、配列の関数の第1引数と第2引数のインデックスの要素を入れ替えます。

//arr=対象の配列
rand.Shuffle(len(arr), func(i, j int) {
    arr[i], arr[j] = arr[j], arr[i] //配列の要素を入れ替える
})

上記のrand.Shuffle()は、要素を入れ替えた配列(array)をシャッフルします。

使用例

package main

import (
	"fmt"
	"math/rand"
	"time"
)

func main() {
	numbers := [5]string{"one", "two", "three", "four", "five"}

	rand.Seed(time.Now().UnixNano()) //乱数のシード設定

	rand.Shuffle(len(numbers), func(i, j int) {
		numbers[i], numbers[j] = numbers[j], numbers[i]
	})

	fmt.Println(numbers)
}
出力:
[four one two five three]

for文

もうひとつは、for文を使う方法です。

まず、「math/rand」をインポートします。

import "math/rand"

次に、for文を配列の長さでループします。

ループ処理で、rand.Intn()を使って乱数を生成し、配列の生成した乱数とループ変数のインデックスの要素を入れ替えます。

//arr=対象の配列
for i := len(arr) - 1; i > 0; i-- {
    j := rand.Intn(i + 1) //乱数の生成
    arr[i], arr[j] = arr[j], arr[i] //要素の入れ替え
}

上記のfor文は、ループした配列(array)をシャッフルします。

シャッフルした新しい配列が欲しい場合は、配列のコピーをシャッフルします。

使用例

package main

import (
	"fmt"
	"math/rand"
	"time"
)

func main() {
	numbers := [5]string{"one", "two", "three", "four", "five"}

	rand.Seed(time.Now().UnixNano()) //乱数のシード設定

        //フィッシャー・イェーツのシャッフル
	for i := len(numbers) - 1; i > 0; i-- {
		j := rand.Intn(i + 1)
		numbers[i], numbers[j] = numbers[j], numbers[i]
	}

	fmt.Println(numbers)
}
出力:
[three four two five one]
スポンサーリンク

まとめ

配列(array)の要素をシャッフルしてランダムに並び替える方法は、次の2つです。

  • rand.Shuffle()を使う方法
    rand.Shuffle(len(arr), func(i, j int) { arr[i], arr[j] = arr[j], arr[i] })
  • for文を使う方法

どちらの方法も配列の要素数でループして、ループ回数分、配列の要素を入れ替えています。

コメント

タイトルとURLをコピーしました