每天一道leetcode(Day 5)


289. 生命游戏

题目描述

根据 百度百科 ,生命游戏,简称为生命,是英国数学家约翰·何顿·康威在 1970 年发明的细胞自动机。

给定一个包含 m × n 个格子的面板,每一个格子都可以看成是一个细胞。每个细胞都具有一个初始状态:1 即为活细胞(live),或 0 即为死细胞(dead)。每个细胞与其八个相邻位置(水平,垂直,对角线)的细胞都遵循以下四条生存定律:

1.如果活细胞周围八个位置的活细胞数少于两个,则该位置活细胞死亡; 2.如果活细胞周围八个位置有两个或三个活细胞,则该位置活细胞仍然存活; 3.如果活细胞周围八个位置有超过三个活细胞,则该位置活细胞死亡; 4.如果死细胞周围正好有三个活细胞,则该位置死细胞复活;

根据当前状态,写一个函数来计算面板上所有细胞的下一个(一次更新后的)状态。下一个状态是通过将上述规则同时应用于当前状态下的每个细胞所形成的,其中细胞的出生和死亡是同时发生的。

示例

  • 示例一

输入:
[
  [0,1,0],
  [0,0,1],
  [1,1,1],
  [0,0,0]
]
输出:
[
  [0,0,0],
  [1,0,1],
  [0,1,1],
  [0,1,0]
]

解题思路

这道题题意是:扫描一个数字,看他附近的 8 个元素(可能没有 8 个),分别对应以上列出的 4 个条件,更新数字。

代码

/**
 * @param {number[][]} board
 * @return {void} Do not return anything, modify board in-place instead.
 */
var gameOfLife = function(board) {
  let row = board.length;
  let col = board[0].length;
  let helper = function(ro, co, copy) {
    let count = 0; // 计算存活的细胞数
    if (ro > 0) {
      count += copy[ro - 1][co];
      if (co > 0) {
        count += copy[ro - 1][co - 1];
      }
      if (co < col - 1) {
        count += copy[ro - 1][co + 1];
      }
    }
    if (ro < row - 1) {
      count += copy[ro + 1][co];
      if (co > 0) {
        count += copy[ro + 1][co - 1];
      }
      if (co < col - 1) {
        count += copy[ro + 1][co + 1];
      }
    }
    if (co > 0) {
      count += copy[ro][co - 1];
    }
    if (co < col - 1) {
      count += copy[ro][co + 1];
    }
    //根据状态进行归类,true为状态变化的,即死变活,活变死
    if (copy[ro][co] == 1) {
      if (count < 2) {
        return true;
      } else if (count > 3) {
        return true;
      }
    }
    if (copy[ro][co] == 0 && count == 3) return true;
    return false;
  };
  let copy = JSON.parse(JSON.stringify(board));
  for (let i = 0; i < row; i++) {
    for (let j = 0; j < col; j++) {
      if (helper(i, j, copy)) {
        //直接通过异或运算变更状态
        board[i][j] ^= 1;
      }
    }
  }
};

文章作者: CassielLee
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 CassielLee !
评论
  目录