Quantcast
Channel: 午後わてんのブログ
Viewing all articles
Browse latest Browse all 420

エクセルVBAでライフゲームその3

$
0
0

別シートで行っていたセルの探査を配列を使うようにしたら2倍くらい速くなった

イメージ 1
1世代更新にかかった時間
20x20だと0.22秒から0.11秒
40x20だと0.36秒から0.14秒
セル数が増えると余計に差がでてくる

動かしているところ
速くなっていい気分!

その後何色かを選べるようにしたら
イメージ 7
0.11秒だったのが0.15秒まで遅くなったw
でも前回より速いからね

前回との変更点
処理速度向上
生存率のグラフをリアルタイムで変更するようにした
誕生ルールを2つ指定できるようにした
mapの上下左右ループの有無を指定できるようにした
生存し続けたセルの色変化で選べる色を赤、緑、青、水色から選べるようにした
それぞれの色で変化なしもできるようにした
クリアと中止を分けて、中止ボタンはクリアしないで停止するようにした
ゲーム実行中は中止以外のボタンを無効にするようにした



セルの状態を配列に入れる処理の流れ
2次元配列を2つ使う、それぞれA, Bとしたら
  1. Aにmapのすべてのセルの状態(色の有無)を入れる
  2. BにはAを使ってセルの探査結果を入れる

4x2のmap(赤枠)で(0, 0)だけ色付きのセル
イメージ 8
この状態の時に

'現在のmapの状態を返す
'生存セルならTrue、それ以外ならFalseを格納した2次元配列を返す
Function GetState() As Boolean()
    Dim map As Range
    Set map = Range("map")
    '2次元配列を作成、これにセルの状態を入れる
    Dim rc As Long, cc As Long
    rc = map.Rows.Count - 1
    cc = map.Columns.Count - 1
    Dim v() As Boolean
    ReDim v(rc, cc)
    
    Dim x As Long, y As Long
    For x = 0 To rc
        For y = 0 To cc
            'false 0, true -1,塗りつぶしなしなら0、色付きなら-1
            v(x, y) = map.Cells(x + 1, y + 1).Interior.ColorIndex <> xlColorIndexNone
        Next
    Next
    GetState = v
End Function
これが1番の部分になる
2次元配列Aを作ってmapのすべてのセルの状態(色の有無)を入れる
これを実行して返ってきた中身は↓

イメージ 5
2次元配列はセルの並びと同じ感じでx, yの座標みたいになるので
同じように探査できる
色付きならTrue、なしならFalseをいれるようにしてあるので
(0, 0)の要素だけTrueが入っている
で、これを使って

2番のBにはAを使ってセルの探査結果を入れる
このコードが↓

'map全体を探査
'色付きの周囲セルの個数を格納した2次元配列を返す
'           ループなし
Function GetNextLifePointNoLoop() As Long()
    Dim st() As Boolean
    st = GetState '現在のmapの状態を取得
    Dim rc As Long, cc As Long
    rc = UBound(st, 1) 'RowsCount
    cc = UBound(st, 2) 'ColumnCount
    Dim x As Long, y As Long, LifeP As Long
    Dim xx As Long, yy As Long
    Dim v() As Long '配列
    ReDim v(UBound(st, 1), UBound(st, 2))
    
    For x = 0 To rc
        For y = 0 To cc
            LifeP = 0
            
            For i = -1 To 1
                For j = -1 To 1
                    
                    'Offset位置の調整、配列の外側に出たらなにもしない
                    xx = x + i
                    yy = y + j
                    If Not (i = 0 And j = 0) Then
                        If Not (xx < 0 Or xx > rc Or yy < 0 Or yy > cc) Then
                            If st(xx, yy) = True Then
                                LifeP = LifeP + 1 '色付きならカウントアップ
                            End If
                        End If
                    End If
                Next j
            Next i
            'カウントを記入
            v(x, y) = LifeP
            
        Next
    Next
    GetNextLifePointNoLoop = v
End Function
配列の中で探査している
周囲8個のセルで色がついている数を配列Bに入れていく
これで返ってくる中身は
イメージ 4
こう

イメージ 2
この状態のときは

イメージ 3
こんな感じで自分の周りで色付きのセルの個数がそれぞれ入っている

後はこの数値とルールを比べて色を塗ったり消したりするだけ
基本ルールだと3個あれば誕生するので
(0, 2)と(1, 2)が3で自身は空白だからこの2つが黒になって
生存判定だと今生きているセルの判定数値は1だから消滅
なので
□□■□
こうなるはず
イメージ 6


今回のファイル:ライフゲーム3.xlsm
ヤフーボックス


前回の記事
エクセルVBAでライフゲームその2のコードと名前の付いたセル範囲の一覧作成マクロ ( ソフトウェア ) - 午後わてんのブログ - Yahoo!ブログ
http://blogs.yahoo.co.jp/gogowaten/14608298.html















Viewing all articles
Browse latest Browse all 420

Trending Articles