Skip to content
On this page

最大子数组和

给你一个整数数组 nums ,请你找出一个具有最大和的连续子数组(子数组最少包含一个元素),返回其最大和。

子数组 是数组中的一个连续部分。

js
输入:nums = [-2,1,-3,4,-1,2,1,-5,4]
输出:6
解释:连续子数组 [4,-1,2,1] 的和最大,为 6

输入:nums = [1]
输出:1

输入:nums = [5,4,-1,7,8]
输出:23

动态规划 dp[i] = Math.max(nums[i], dp[i - 1] + nums[i]);

js
/**
 * @param {number[]} nums
 * @return {number}
 */
var maxSubArray = function (nums) {
  let dp = [nums[0]];
  let len = nums.length;

  for (let i = 1; i < len; i++) {
    dp[i] = Math.max(nums[i], dp[i - 1] + nums[i]);
  }

  return Math.max(...dp);
};

代码优化

js
var maxSubArray = function (nums) {
  let max = nums[0];
  let pre = max;
  let len = nums.length;
  for (let i = 1; i < len; i++) {
    pre = Math.max(pre + nums[i], nums[i]);
    max = Math.max(max, pre);
  }

  return max;
};

最长重复子数组

力扣题目链接: 给两个整数数组  A  和  B ,返回两个数组中公共的、长度最长的子数组的长度。

js
输入:
A: [1,2,3,2,1]
B: [3,2,1,4,7]
输出:3
解释:长度最长的公共子数组是 [3, 2, 1] 。

动态规划

js
const findLength = (A, B) => {
  const m = A.length;
  const n = B.length;
  const dp = new Array(m + 1);
  for (let i = 0; i <= m; i++) {
    // 初始化整个dp矩阵,每个值为0
    dp[i] = new Array(n + 1).fill(0);
  }
  let res = 0;
  // i=0或j=0的base case,初始化时已经包括
  for (let i = 1; i <= m; i++) {
    // 从1开始遍历
    for (let j = 1; j <= n; j++) {
      // 从1开始遍历
      if (A[i - 1] == B[j - 1]) {
        dp[i][j] = dp[i - 1][j - 1] + 1;
      } // A[i-1]!=B[j-1]的情况,初始化时已包括了
      res = Math.max(dp[i][j], res);
    }
  }
  return res;
};

滑动窗口解法

非常好理解,想象两把尺子,错开之后比较相同的部分,找最长相同的串就好了。

Released under the MIT License.