当前位置: 首页 > article >正文

前缀和(7)_连续数组

个人主页:C++忠实粉丝
欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 C++忠实粉丝 原创

前缀和(7)_连续数组

收录于专栏【经典算法练习】
本专栏旨在分享学习算法的一点学习笔记,欢迎大家在评论区交流讨论💌

目录

1. 题目链接 :

2. 题目描述 :

3. 解法(一维前缀和) :

    算法思路 :

   示例说明:

    代码展示 :

    结果分析:

 


1. 题目链接 :

OJ链接: 连续数组

2. 题目描述 :

给定一个二进制数组 nums , 找到含有相同数量的 0 和 1 的最长连续子数组,并返回该子数组的长度。

示例 1:

输入: nums = [0,1]
输出: 2
说明: [0, 1] 是具有相同数量 0 和 1 的最长连续子数组。

示例 2:

输入: nums = [0,1,0]
输出: 2
说明: [0, 1] (或 [1, 0]) 是具有相同数量0和1的最长连续子数组。

提示:

  • 1 <= nums.length <= 105
  • nums[i] 不是 0 就是 1

3. 解法(一维前缀和) :

    算法思路 :

转换 0 和 1:

将 0 视作 - 1,而 1 保持不变。这意味着在计算前缀和时,0 会减少总和。
这样,当某段区间内的 0 和 1 数量相同时,前缀和将回到相同的值。

计算前缀和:

遍历数组时,维护一个变量 sum 用来表示当前的前缀和。
如果在某个位置的 sum 值与之前某个位置的 sum 值相同,说明从这两个位置之间的元素(即子数组)中,0 和 1 的数量相等。

使用哈希表记录前缀和的索引:

使用一个哈希表 dp 来存储每个前缀和第一次出现的索引。
初始化 dp[0] = -1,表示前缀和为 0 的情况下,虚拟的索引是 - 1,这有助于处理从数组起始位置开始的有效子数组。

判断条件:

在遍历数组时,每当计算新的前缀和 sum:
        如果 sum 已经在 dp 中存在(即 dp.count(sum) 为真),这意味着从 dp[sum] + 1 到当前索引 i 的这段区间中,0 和 1 的数量相等。
        通过计算当前索引 i 与 dp[sum] 的差值得到这段子数组的长度:i - dp[sum]。

   示例说明:

假设有一个数组 nums = [0, 1, 0, 1],我们可以按以下步骤分析前缀和的变化:

初始状态:

dp = { 0: -1 }
sum = 0
ret = 0

遍历数组:

i = 0, nums[0] = 0:
        sum = 0 + (-1) = -1
        dp[-1] 不存在,所以将 dp[-1] = 0。
i = 1, nums[1] = 1 :
    sum = -1 + 1 = 0
    dp[0] 已存在,表示从 dp[0] + 1 到 i 的子数组有相同数量的 0 和 1,长度为 1 - (-1) = 2,更新 ret = 2。

 i = 2, nums[2] = 0 :
    sum = 0 + (-1) = -1
    dp[-1] 已存在,长度为 2 - 0 = 2,ret 不变。

i = 3, nums[3] = 1 :
    sum = -1 + 1 = 0
    dp[0] 已存在,长度为 3 - (-1) = 4,更新 ret = 4。

    代码展示 :

class Solution {
public:
    int findMaxLength(vector<int>& nums) {
        unordered_map<int, int> dp;
        dp[0] = -1;
        int sum = 0, ret = 0;
        for(int i = 0; i < nums.size(); i++)
        {
            sum += nums[i] == 0 ? -1 : 1;
            if(dp.count(sum)) ret = max(ret, i - dp[sum]);
            else dp[sum] = i;
        } 
        return ret;
    }
};

 

    结果分析:

时间复杂度和空间复杂度
时间复杂度 :O(n),其中n 是数组的长度。我们只遍历数组一次。
空间复杂度 :O(n),在最坏情况下,哈希表可能存储所有的前缀和。

 


http://www.kler.cn/news/327987.html

相关文章:

  • 安全教育培训小程序系统开发制作方案
  • Thinkphp/Laravel小型超市进销存管理系统的设计与实现
  • Study-Oracle-10-ORALCE19C-RAC集群搭建(一)
  • Python 在自动化运维时常用到的方法
  • 移情别恋c++ ദ്ദി˶ー̀֊ー́ ) ——15.红黑树
  • C# C++ 笔记
  • 使用cmake配置pcl环境
  • 基于云开发进行快速搭建企业智能名片小程序
  • 考研数据结构——顺序表代码题
  • SQL进阶技巧:影院相邻的座位如何预定?
  • 计算机毕业设计Hadoop+Spark知识图谱体育赛事推荐系统 体育赛事热度预测系统 体育赛事数据分析 体育赛事可视化 体育赛事大数据 大数据毕设
  • B树简介:高效数据存储与检索的利器
  • RabbitMQ应用
  • @SpringBootTest 和 @Test的区别
  • 高效处理大规模数据:MATLAB实践指南
  • C#基于SkiaSharp实现印章管理(9)
  • 基于Spring Boot的校园管理系统
  • linux部署redis,整合ansible和redis
  • 如何在算家云搭建MVSEP-MDX23(音频分离)
  • 深度学习500问——Chapter17:模型压缩及移动端部署(2)
  • ubuntu安装ftp服务器
  • 前端Vue.js与后端Flask/Django协同开发指南
  • Java面试题真题·人才招聘系统项目介绍
  • 【Java 集合】List接口 —— ArrayList 与 LinkedList 详解
  • 针对考研的C语言学习(定制化快速掌握重点2)
  • 深度解析 HTTP
  • Linux集群部署RabbitMQ
  • 从Linux系统的角度看待文件-基础IO
  • Linux服务器配置anaconda3,下载torch
  • Brave编译指南2024 MacOS篇-拉取源码前的准备工作(二)