繁体   English   中英

生命游戏:尝试用新算法提高计算效率,而不是减少。 为什么?

[英]Game of Life: Tried to increase computation efficiency with new algorithm, reduced in stead. Why?

我正在编写康威的生命游戏,并制作了一个工作顺畅的JS程序。 我在工作版本中做的是检查网格中每个坐标的每个相邻坐标,并根据其邻居数量杀死或生成它。 现在,我想通过跟踪哪些坐标是活着的,并且只处理那些和它们的邻居而不是整个网格来使算法更有效。 我做了这个替代计划:

var g = 0;
var cellMatrix = new Array();
var height = 68;  
var width = 100;
var livingCellIndex = 0;
var livingCells = new Array();

writeBoard();
declareFirstGeneration();
live();

function live() {

    processGeneration();
    g++;
    setTimeout(live, speed);

}

function declareNextGeneration() {

    livingCells[g + 1] = new Array();

    cellMatrix[g + 1] = new Array();

    for (var x = 0; x < width; x++) {

        cellMatrix[g + 1][x] = new Array();

        for (var y = 0; y < height; y++) {

            cellMatrix[g + 1][x][y] = false;
        }
    }
}

function declareFirstGeneration() {

    livingCells[g] = new Array();

    cellMatrix[g] = new Array();

    for (var x = 0; x < width; x++) {

        cellMatrix[g][x] = new Array();

        for (var y = 0; y < height; y++) {

            cellMatrix[g][x][y] = false;
        }
    }
}

function processGeneration() {

    declareNextGeneration();

    livingCellIndex = 0;

    var x, y;

    for (var i = 0; i < livingCells[g].length; i++) {

        x = livingCells[g][i][0];
        y = livingCells[g][i][1];

        numberOfNeighbors = getLivingNeighbors(x, y);
        //console.log("numberOfNeighbors", numberOfNeighbors);
        if (numberOfNeighbors == 2 || numberOfNeighbors == 3) {
            spawnCell(g + 1, x, y);
        } else {
            killCell(g + 1, x, y);
        }

        for (var neighborX = x - 1; neighborX <= x + 1; neighborX++) {
            for (var neighborY = y - 1; neighborY <= y + 1; neighborY++) {
                if (neighborX < width && neighborX >= 0 && neighborY < height && neighborY >= 0) {
                    numberOfNeighbors = getLivingNeighbors(neighborX, neighborY);
                    //console.log(g, neighborX, neighborY, "has ", numberOfNeighbors, " neighbors");
                    if (numberOfNeighbors == 3) {
                        spawnCell(g + 1, neighborX, neighborY);
                    }
                }
            }
        }
    }
    refreshGenerationDisplay(x,y);
}

function spawnCell(g, x, y) {

    cellMatrix[g][x][y] = true;
    livingCells[g][livingCellIndex] = new Array(2);
    livingCells[g][livingCellIndex][0] = x;
    livingCells[g][livingCellIndex][2] = y;
    document.getElementById(x + '-' + y).style.background = "green"; // visual grid 
    livingCellIndex++;
}


function killCell(g, x, y) {
    cellMatrix[g][x][y] = false;
    document.getElementById(x + '-' + y).style.background = "none"; // visual grid
}

但我发现它比我的第一个程序要慢得多。 似乎计算每一代的计算成本似乎随着每一代而增加。 这让我感到惊讶,因为我在这个替代算法中处理的数据较少。 我不确定它是否有意义,但这是第一个版本:

var g = 0;
var cellMatrix = new Array();
var height = 68;  
var width = 100;

declareThisGeneration();

function live() {

    g++;

    processGeneration();
    setTimeout(live, speed);

}

function processGeneration() {

    if (oscillation) adjustGForOscillation();
    if (g > 0) {
        processNormalGeneration();
    } else {
        processFirstGeneration();
    }
}

function processFirstGeneration() {

    for (var x = 0; x < width; x++) {                
        for (var y = 0; y < height; y++) {
            processFirstGenCell(g, x, y);
        }
    }
}

function processFirstGenCell(g, x, y) {

    if (cellMatrix[g][x][y]) { //if alive
        spawnCell(g, x, y);
    } else { //if dead
        killCell(g, x, y);
    }
}


function processNormalGeneration() {

    for (var x = 0; x < width; x++) {                
        for (var y = 0; y < height; y++) {
            processCell(g, x, y);
        }
    } 
}

function processCell(g, x, y) {

    var livingNeighbors = getLivingNeighbors(g - 1, x, y);

    if (cellMatrix[g - 1][x][y]) { //if alive
        if (livingNeighbors != 2 && livingNeighbors != 3) {
            killCell(g, x, y);
        } else {
            spawnCell(g, x, y);
        }
    } else { //if dead
        if (livingNeighbors == 3) {
            spawnCell(g, x, y);
        } else {
            killCell(g, x, y);
        }
    }
}

function spawnCell(g, x, y) {
    cellMatrix[g][x][y] = true;
    document.getElementById(x + '-' + y).className = 'alive';
}

function killCell(g, x, y) {

    cellMatrix[g][x][y] = false;
    document.getElementById(x + '-' + y).className = ''
}

我的问题是,是什么让“改进”的算法如此缓慢,我怎样才能降低成本呢?

版本1 //首先,最快

版本2 //新,慢

你不断在新版本中为每一代分配新的数组; 在旧版本中,您将继续重复使用相同的网格。 除了速度慢之外,如果不是因为速度慢,那么你的内存占用量会不断增长。

一种可能的解释是,如果你跟踪太多事情,计算机将需要分配更多的内存来存储它们,这需要时间。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM