leetcode每天一题:【杨辉三角2】(简单)

143 阅读1分钟

这是我参与2022首次更文挑战的第35天,活动详情查看:2022首次更文挑战

题目描述

leetcode题目地址

给一个正整数索引rowIndex,然后需要你返回杨辉三角的第rowIndex行。

什么是杨辉三角?

image.png

就是左斜边和右斜边都是1,然后空白的地方是等于上一级的左上方和右上方相加的值。

//  1
// 1  1
// 1 2 1
// 1 3 3 1
// 1 4 6 4 1 
// 1 5 10 10 5 1

如果numRows为 1,则返回 [1, 1]

如果numRows2,则返回 [1,2,1]

如果numRows3,则返回 [1,3,3,1]

这个题目跟上一篇文章类似,不过上一篇是返回前numRows行所有的杨辉三角。

这个题目是求第rowIndex行的杨辉三角。

思路分析

第一种方法

上面说到,上一篇文章是求前numRows行所有的杨辉三角,今天这个是求第rowIndex行的杨辉三角。

所以我们可以在之前的基础上返回第rowIndex行的杨辉三角就行。

代码如下

/**
 * @param {number} rowIndex
 * @return {number[]}
 */
var getRow = function (rowIndex) {
  const arr = []
  for (let i = 0; i < rowIndex + 1; i++) {
    const item = [1]
    for (let j = 1; j < i; j++) {
      const a = arr[i - 1][j - 1]
      const b = arr[i - 1][j]
      item.push(a + b)
    }
    if (i !== 0) {
      item.push(1)
    }
    arr.push(item)
  }
  return arr[rowIndex]
};

image.png

第二种方法

那能不能不要把所有的杨辉三角生成到二维数组中再返回。

可以。

我们可以利用变量cur,代表当前的杨辉三角,变量pre,代表上一行的杨辉三角,生成一行,就覆盖上一行。以此类推,最后只生成需要的那一行。

遍历结束后,返回cur即可。

/**
 * @param {number} rowIndex
 * @return {number[]}
 */
var getRow = function (rowIndex) {
  let cur = []
  let pre = []
  for (let i = 0; i < rowIndex + 1; i++) {
    cur = [1]
    for (let j = 1; j < i; j++) {
      const a = pre[j - 1]
      const b = pre[j]
      cur.push(a + b)
    }
    if (i !== 0) {
      cur.push(1)
    }
    pre = cur
  }
  return cur
};

image.png

第三种方法

再优化一下,能不能只通过一个数组就实现?

可以。

我们首先先生成目标长度的数组,并且填充0。

然后把它第一项设置为1。

然后对它进行遍历,第一层是常规遍历,索引从1开始(因为第0位无需处理了),第二层是对它从后往前遍历。

从后往前叠加,并赋值。

比如:

rowIndex: 3

row: [1,0,0,0]

第一次遍历: [1,1,0,0]

第二次遍历: [1,2,1,0]

第三次遍历: [1,3,3,1]

返回即可。

为什么是从后往前遍历?

因为它后面都是0,从最后一个,加上前一个,赋值给最后一个,依此类推。不会影响到前面的叠加。

代码如下:

var getRow = function (rowIndex) {
  const row = new Array(rowIndex + 1).fill(0);
  row[0] = 1;
  for (let i = 1; i <= rowIndex; ++i) {
    for (let j = i; j > 0; j--) {
      row[j] += row[j - 1];
    }
  }
  return row;
};

image.png