JAVA - 康威的生命游戏删除了所有活细胞?

时间:2013-12-17 06:18:21

标签: java

我正在为康威的学校项目的生命游戏工作。我不是直接寻找代码。我希望找出我的代码有什么问题。

在康威的“生命游戏”中,如果一个单元有3个活着的邻居,那么它就会从死到活。如果它有两个或三个活着的邻居,它会保持活着。如果这些都不是真的那就死了。

我的LifeView类有一个显示单元格模拟的方法,然后显示给定点周围有多少活着的单元格。

这是我得到的输出:

How many rows is your simulation?
5
How many columns is your simulation?
5
How many generations is your simulation?
3
xxxxx
xxxxx
xx0xx
xx0xx
xx0xx

00000
01110
02120
03230
02120


xxxxx
xxxxx
xxxxx
xxxxx
xxxxx

00000
00000
00000
00000
00000


xxxxx
xxxxx
xxxxx
xxxxx
xxxxx

00000
00000
00000
00000
00000

这是错误的,因为第二代应该是穿过第一代活细胞中心的活细胞的水平线。所有细胞都没有穿过那个中心。我很难过为什么它不起作用。

主要课程:

package gameOfLife;

import java.util.Scanner;

public class Main {

/**
 * @param args the command line arguments
 */
public static void main(String[] args)
{
    Scanner numReader = new Scanner(System.in);
    System.out.println("How many rows is your simulation?");
    int rows = numReader.nextInt();
    System.out.println("How many columns is your simulation?");
    int columns = numReader.nextInt();
    System.out.println("How many generations is your simulation?");
    int generations = numReader.nextInt();


    LifeModel model = new LifeModel(rows,columns);
    LifeView life = new LifeView(model);

    for(int i=0; i<generations; i++)
    {
         life.displayLife();
         model.nextGeneration();
    }

}

LifeView类:

package gameOfLife;

import java.util.Scanner;

public class LifeView {

private LifeModel model;

public LifeView(LifeModel model)
{
    this.model = model;
}


public void displayLife()
{
    for(int i=0; i < model.getWorld().length; i++)
    {
        for(int j=0; j < model.getWorld()[0].length; j++)
        {

            if(model.getWorld()[i][j])
            {
                System.out.print("0");
            }
            else
            {
                System.out.print("x");
            }
        }
        System.out.println("");
    }
    System.out.println("");

    for(int i=0; i < model.getWorld().length; i++)
    {
        for(int j=0; j < model.getWorld()[0].length; j++)
        {

            System.out.print(model.numLivingNeighbors(i,j));
        }
        System.out.println("");
    }
    System.out.println("");
    System.out.println("");
}
}

LifeModel类:     包gameOfLife;

public class LifeModel
{
private boolean[][] world;
private int numRows;
private int numCols;
private boolean[][] tempWorld;



public LifeModel(int rows, int cols)
{
    this.numRows=rows;
    this.numCols=cols;
    world = new boolean[rows][cols];
    initWorld();
    tempWorld = world;
}

private void initWorld()
{

    boolean done = false;

    while(!done)
    {
        int i = (int) (Math.random()*numRows);
        int j = (int) (Math.random()*numCols);
        if(j>0 && i>0 && i<numRows-1 && j<numCols-1)
        {
            /*
             world[i-1][j-1] = true;
             world[i-1][j] = true;
             world[i-1][j+1] = true;
             world[i][j+1] = true;
             world[i+1][j] = true;
             */
             world[i][j]=true;
             world[i+1][j]=true;
             world[i-1][j]=true;
             done = true;
        }
    }


}

public void nextGeneration()
{
    //tempWorld = new boolean[numRows+2][numCols+2];

    int rows = world.length;
    int columns = world[0].length;

    for(int i=0; i < rows; i++)
    {
        for(int j = 0; j < columns; j++)
        {
            toggleCell(i,j);
        }
    }
    world = tempWorld;
}

public void toggleCell(int r, int c)
{
    int count = numLivingNeighbors(r,c);
    if(!world[r][c] && count==3)
    {
        tempWorld[r][c] = true;
    }
    else if(world[r][c] && (count>=2 && count<=3))
    {
        tempWorld[r][c] = true;
    }
    else
    {
        tempWorld[r][c] = false;
    }
}

public int numLivingNeighbors(int r, int c)
{
    int count = 0;
    boolean newCells[][] = world;
    for(int i = -1; i<=1; i++)
    {
        for(int j = -1; j<=1; j++)
        {
            if(i!=0 || j!=0)
            {
                int row = r + i;
                int column = c + j;
                if(row>=0 && row < newCells.length && column>=0 && column<newCells[0].length && newCells[row][column])
                {
                    count++;
                }
            }
        }
    }
    return count;
}

public void userChange()
{

}

public boolean[][] getWorld()
{
    return world;
}


}

非常感谢任何帮助!

3 个答案:

答案 0 :(得分:4)

您的LifeModel类只有几个小问题。

在构造函数中,您将tempWorld设置为引用与实际游戏世界相同的数组。这将导致对tempWorld的任何修改也会影响gameWorld。

public LifeModel(int rows, int cols)
{
    this.numRows=rows;
    this.numCols=cols;
    world = new boolean[rows][cols];
    initWorld();
    //tempWorld = world;  // You can remove this line.
}

然后在下一代你有“// tempWorld = new boolean [numRows + 2] [numCols + 2];”评论说。你真的需要在这里创建一个新的临时数组,这样你就不会在阅读时更改游戏板。但是,我不确定+2应该是什么,所以我删除了它。你应该:

public void nextGeneration()
{
    tempWorld = new boolean[numRows][numCols]; // Keep it the same size

    int rows = world.length;
    int columns = world[0].length;

    for(int i=0; i < rows; i++)
    {
        for(int j = 0; j < columns; j++)
        {
            toggleCell(i,j);
        }
    }
    world = tempWorld;
}

在我做出这些改变后,它对我来说非常有效。我已经在我的机器上使用了下面的完整LifeModel类。

package gameOfLife;

public class LifeModel
{
private boolean[][] world;
private int numRows;
private int numCols;
private boolean[][] tempWorld;



public LifeModel(int rows, int cols)
{
    this.numRows=rows;
    this.numCols=cols;
    world = new boolean[rows][cols];
    initWorld();
}

private void initWorld()
{

    boolean done = false;

    while(!done)
    {
        int i = (int) (Math.random()*numRows);
        int j = (int) (Math.random()*numCols);
        if(j>0 && i>0 && i<numRows-1 && j<numCols-1)
        {
            /*
             world[i-1][j-1] = true;
             world[i-1][j] = true;
             world[i-1][j+1] = true;
             world[i][j+1] = true;
             world[i+1][j] = true;
             */
             world[i][j]=true;
             world[i+1][j]=true;
             world[i-1][j]=true;
             done = true;
        }
    }


}

public void nextGeneration()
{
    tempWorld = new boolean[numRows][numCols];

    int rows = world.length;
    int columns = world[0].length;

    for(int i=0; i < rows; i++)
    {
        for(int j = 0; j < columns; j++)
        {
            toggleCell(i,j);
        }
    }
    world = tempWorld;
}

public void toggleCell(int r, int c)
{
    int count = numLivingNeighbors(r,c);
    if(!world[r][c] && count==3)
    {
        tempWorld[r][c] = true;
    }
    else if(world[r][c] && (count>=2 && count<=3))
    {
        tempWorld[r][c] = true;
    }
    else
    {
        tempWorld[r][c] = false;
    }
}

public int numLivingNeighbors(int r, int c)
{
    int count = 0;
    boolean newCells[][] = world;
    for(int i = -1; i<=1; i++)
    {
        for(int j = -1; j<=1; j++)
        {
            if(i!=0 || j!=0)
            {
                int row = r + i;
                int column = c + j;
                if(row>=0 && row < newCells.length && column>=0 && column<newCells[0].length && newCells[row][column])
                {
                    count++;
                }
            }
        }
    }
    return count;
}

public void userChange()
{

}

public boolean[][] getWorld()
{
    return world;
}


}

答案 1 :(得分:0)

检查numLivingNeighbors是否为世界上的每个单元格返回正确的值。

同时检查生存的步骤

答案 2 :(得分:0)

嘿,你在代码中犯了一个简单的错误

public LifeModel(int rows, int cols)
{
    this.numRows=rows;
    this.numCols=cols;
    world = new boolean[rows][cols];
    initWorld();
    tempWorld = world;
}

这是LifeModel构造函数。 在这个构造函数中,您还需要初始化tempworld。你不应该将你的世界分配给tempworld。 修改后,这段代码将变成这样....

public LifeModel(int rows, int cols)
{
this.numRows=rows;
this.numCols=cols;
world = new boolean[rows][cols];
tempWorld = new boolean[rows][cols];
initWorld();
}

在此之后输出将是正确的。