Сравнение двумерно массива в цикле с предыдущий итерацией [дубликат]

294
19 июня 2017, 22:17

Данный вопрос уже был задан и имеет решение:

  • Программирование конца игры в игре Конвея “Жизнь”

Пишу вариацию игры "Жизнь" (Conway's Game of Life). Логика самой игры представлена двумерным массивом который делит поле на аккуратные квадратики. Если в ячейке "1", клетку закрашиваем (это живая клетка), если ноль - клетка мертвая, цвета нет.

Сам вопрос Хочу выводить сообщение "игра окончена" когда в новой итерации цикла количество живых клеток не изменилось по отношению к предыдущей. Для этого я так понимаю мне нужно сравнить текущие значение массивов с значением в предыдущей итерацией. То-есть проверить количество живых ячеек с "1" cейчас с количеством ячеек с "1" в предыдущей итерации. Но у меня не выходи это сделать. Подскажите как это делается. можно с примером. Спасибо.

https://jsfiddle.net/pridan/g0c7okmL/

(function() {
  // initialParams();
  // function initialParams() {
  //
  //
  // }
  // var enterSize = prompt("Введите размер поля?", "");
  // var enterSpeed = prompt("Введите скорость?", "");
  var canvas = document.getElementById('canvas');
  var ctx = canvas.getContext('2d');
  var size = 500;
  var meshSize = size / 10;
  canvas.width = size;
  canvas.height = size;
  var speed = 100;
  var arr = [];
  var count = 0;
  var countPopulation = 0;
  var countLive = 0;
  var timer;
  init();
  function init() {
    initButtons();
    initGameFiaeld();
  }
  //вызов очистки поля
  function clear() {
    stop();
    clearCanvas();
    resetGenerations();
    resetGameField();
    canvasBoard();
  }
  //Рамка игрового поля
  var canvasBoard = function() {
    ctx.strokeStyle = "#000";
    ctx.strokeRect(0, 0, size, size);
  };
  canvasBoard();
  //Рамка игрового поля функция очистки поля
  function clearCanvas() {
    var canvas = document.getElementById('canvas');
    var ctx = canvas.getContext('2d');
    ctx.clearRect(0, 0, size, size);
  }
  function drawPoint() {
    ctx.clearRect(0, 0, size, size);
    for (var i = 0; i < meshSize; i++) {
      for (var j = 0; j < meshSize; j++) {
        if (arr[i][j] == 1) {
          countPopulation += 1;
          ctx.fillRect(j * 10, i * 10, 10, 10);
        }
      }
    }
  }
  //Рисуем точки
  function initGameFiaeld() {
    canvas.addEventListener('click', clickPosition);
    function clickPosition(event) {
      var x = event.offsetX;
      var y = event.offsetY;
      x = Math.floor(x / 10);
      y = Math.floor(y / 10);
      for (var i = 0; i < meshSize; i++) {
        for (var j = 0; j < meshSize; j++) {
          if (arr[i][j] == 0) {
            arr[y][x] = 1;
          }
        }
      }
      arr[y][x] = 1;
      drawPoint();
      canvasBoard();
    }
    //Размечаю поле
    var goLIfe = function() {
      for (var i = 0; i < meshSize; i++) {
        arr[i] = [];
        for (var j = 0; j < meshSize; j++) {
          arr[i][j] = 0;
        }
      }
    }();
  }
  //Функция сброса очистки поля
  function resetGameField() {
    for (var i = 0; i < meshSize; i++) {
      for (var j = 0; j < meshSize; j++) {
        if (arr[i][j] == 1) {
          arr[i][j] = 0;
        }
      }
    }
    drawPoint();
  }
  //Иницилизация кнопок
  function initButtons() {
    var startBtn = document.getElementById('start-evolution');
    var stopBtn = document.getElementById('stop-evolution');
    var clearBtn = document.getElementById('clear');
    startBtn.addEventListener('click', function() {
      start();
      startBtn.setAttribute('disabled', true);
    });
    stopBtn.addEventListener('click', function() {
      stop();
      startBtn.removeAttribute('disabled', true);
    });
    clearBtn.addEventListener('click', clear);
  }
  //Проверка условий существования точек
  function startLife() {
    var arr2 = [];
    for (var i = 0; i < meshSize; i++) {
      arr2[i] = [];
      for (var j = 0; j < meshSize; j++) {
        var neighbors = 0;
        if (arr[checkMinus(i) - 1][j] == 1) neighbors++;
        if (arr[i][checkPlus(j) + 1] == 1) neighbors++;
        if (arr[checkPlus(i) + 1][j] == 1) neighbors++;
        if (arr[i][checkMinus(j) - 1] == 1) neighbors++;
        if (arr[checkMinus(i) - 1][checkPlus(j) + 1] == 1) neighbors++;
        if (arr[checkPlus(i) + 1][checkPlus(j) + 1] == 1) neighbors++;
        if (arr[checkPlus(i) + 1][checkMinus(j) - 1] == 1) neighbors++;
        if (arr[checkMinus(i) - 1][checkMinus(j) - 1] == 1) neighbors++;
        if (arr[i][j] == 0) {
          arr2[i][j] = neighbors == 3 ? 1 : 0;
        } else {
          arr2[i][j] = neighbors == 2 || neighbors == 3 ? 1 : 0;
        }
      }
    }
    arr = arr2;
    drawPoint();
    canvasBoard();
    count++;
    timer = setTimeout(startLife, speed);
    updateGenerations();
    updatePopulation(innerUpdatePopulation);
  }

  //Cчётчик для подсчёта живых клеток
  function updatePopulation(param) {
    countPopulation = 0;
    for (var i = 0; i < meshSize; i++) {
      for (var j = 0; j < meshSize; j++) {
        if (arr[i][j] == 1) {
          console.log(arr);
          countPopulation += 1;
        }
      }
    }
    param();
  }
  function innerUpdatePopulation() {
    var populationDiv = document.getElementById('cell-life');
    populationDiv.innerHTML = countPopulation;
  }
  //Счетчик циклов(поколений)
  function updateGenerations() {
    var generationDiv = document.getElementById('count');
    generationDiv.innerHTML = count;
  }
  //Конец игры
  function gameOver() {
  }

  //Сброс циклов(поколений)
  function resetGenerations() {
    count = 0;
    updateGenerations();
  }
  //Проверка границ
  function checkMinus(i) {
    if (i == 0) return meshSize;
    else return i;
  }
  //Проверка границ
  function checkPlus(i) {
    if (i == meshSize - 1) return -1;
    else return i;
  }
  function start() {
    startLife();
  }
  function stop() {
    clearTimeout(timer);
  }
})();
<canvas id='canvas'></canvas>
<p>Циклы</p><span id="count">0</span>
<p>Популяция</p>
<div id="cell-life">0</div>
<button id="start-evolution">Start</button>
<button id="stop-evolution">Stop</button>
<button id="next-generation" hidden>Next</button>
<button id="clear">Clear</button>
Answer 1

На текущей итерации преобразуете массив в строку, сохраняете, на следующей опять получаете строку и сравниваете со строкой, полученной на предыдущей итерации.

var arrHash = "";
function getArrHash() {
  var currentHash = arr.toString();
  if(arrHash == currentHash) {
    gameOver();
  }
  arrHash = currentHash;
}

Если вам нужно сохранять только количество, тогда так:

var arrHash = 0;
function getArrHash() {
  var currentHash = arr.toString().split(',').reduce(function(sum, v) {
    return +v + sum
  }, 0);
  if (arrHash == currentHash) {
    gameOver();
  }
  arrHash = currentHash;
}
READ ALSO
Какие виды regex поддерживаются браузерами?

Какие виды regex поддерживаются браузерами?

Я столкнулся с тем, что regex в браузере отрабатывает не совсем так как в c# php и других средахВопрос, все ли регулярные выражения работают в браузерах?...

201
Выполнить безопасный запрос с помощью PDO

Выполнить безопасный запрос с помощью PDO

// Как выполнить данный запрос максимально безопасно и просто с помощью PDO

196
Ошибка с PHPMailer

Ошибка с PHPMailer

ЗдравствуйтеПроблема такая: отправляю письма в html формате c помощью phpmailer, а мне на экран выводится кучу разное информации об отправлении,...

222