大学生の雑記

色々なものを書いています 旧:旧帝大生の雑記ブログ

Processingでセルオートマトン①: ライフゲームのパターンを総当たりする


スポンサードリンク

次の記事
coronene.hatenablog.com


Conwayのライフゲームとはセルオートマトンの一種です。ゲームは、2次元のセルのグリッドから成り立ち、それぞれのセルは生きているか死んでいるかの2つの状態のいずれかにあります。各セルの状態は、その周りの8つのセルの状態によって決まり、一連のルールに従っています。

ライフゲームのルールは次のとおりです。

周りに生きているセルが2つ未満の場合、そのセルは過疎により死滅します。
周りに生きているセルが2つか3つの場合、そのセルは次の世代に生き続けます。
周りに生きているセルが3つ以上の場合、そのセルは過密により死滅します。
死んでいるセルが正確に3つの生きているセルに囲まれている場合、そのセルは再生によって生き返ります。



ところでこれよりも簡単な一次元セルオートマトンというものがあるのですが、それの規則は二進数コードで記述できます。これを拡張してライフゲームの規則も二進数コードで記述できるようにしてみました。

周囲の生きているセルが何個あるかで次の生死を決定するので、周囲の生きているセルの個数ごとに生死を対応付けしてそれを順番に並べると二進数になります。それを利用して書いたのが以下のコードです。一次元版とそう変わらないものになりました。

int[] rule = new int[9];
int[] rule2 = new int[9];

int len;
int col, row;
int[][] c;
boolean pause = false;
int n = 0;


void setup(){
    frameRate(6);
    size(600, 600);
    
    len = 6; 
    col = width/len;
    row = height/len;
    
    c = new int[col][row];

    //最初の配置
    for(int i = 0; i < col-1; i ++){
    for(int j = 0; j < row-1; j ++){
        //c[i][j] = 0; //生命無し
        float r = random(1);
                    if(r <= 0.3){ 
                    c[i][j] = 1;
                    
        //c[i][j] = floor(random(2)); //ランダム
                    
                    }
    }
    
     int ruleNumber = 32;//規則の指定(0~512) Born 
     int ruleNumber2 = 96; //規則の指定(0~512)Survives
    
     
   
    
    //数字から規則へ変換
    String b = binary(ruleNumber); //二進数に変換
    String b2 = binary(ruleNumber2);
    
    String[] r = b.split("", b.length()); //1文字ずつに分ける
    String[] r2 = b2.split("", b2.length());
    
    
    for(int l = 0; l <= 8; l ++){
        rule[l] = int(r[l+23]); //最後の8文字だけ取り出す
        
        rule2[l] = int(r2[l+23]);
    }
  
    
}
}

void draw(){
    background(255);
    
    //セルの描画
    for(int i = 0; i < col; i ++){
    for(int j = 0; j < row; j ++){
        noStroke();
        fill((1-c[i][j] % col)*255, 255, 200);
        rect(i*len, j*len, len, len);
    }
    }
    
    
    
    
   

  
   
        int[][] next = new int[col][row];
        for(int i = 1; i <= col+1; i ++){
        for(int j = 1; j <= row+1; j ++){
            //周囲8マスの生きているセルの数を計算
            
            int neighbors =    c[(i-1) % col][(j-1) % col] + c[(i) % col][(j-1) % col] + c[(i+1) % col][(j-1) % col]
                             + c[(i-1) % col][(j) % col]                               + c[(i+1) % col][(j) % col]
                             + c[(i-1) % col][(j+1) % col] + c[(i) % col][(j+1) % col] + c[(i+1) % col][(j+1) % col];
            
            
            
            else
              for(int k = 0; k <= 8; k ++){
                if(neighbors == k){
                  if(c[i % col][j % col] == 0){
                    next[i % col][j % col] = rule[k];
                  }
                  if(c[i % col][j % col] == 1){
                    next[i % col][j % col] = rule2[k];
                  }
                }
              }
                
        }
        }
            
      

        
        
        c = next; //次のステップの配置を適用
    }
    

| |<

nuleNumber = 32でruleNumber2 = 96のときが通常のライフゲームとなっています。