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

【低成本扩容】动态扩容实战指南

面对扩容操作时,下面这种操作是否也会迷惑你?下面来为大家解惑~

size_t newcapacity = 2*_capacity > (_size + len)?2*_capacity:(_size+len);
//len为即将插入的字符串有效字符个数//_size为当前字符串有效字符个数//_capacity为当前容量大小//newcapacity为扩容后容量大小

一、为什么需要动态扩容?

静态数组(如 C 语言的int arr[10])的容量是固定的,一旦存储的元素数量超过容量,就会发生溢出。而动态数组(如 C++ 的vector、Java 的ArrayList)需要支持灵活添加元素,因此必须在容量不足时自动扩容。

但扩容的过程是 "昂贵" 的:

  • 需要申请一块更大的内存空间
  • 把原有元素复制到新空间
  • 释放旧空间的内存

如果每次添加元素都只扩容 1 个单位,会导致频繁扩容(添加 n 个元素可能需要 n 次扩容),时间复杂度会退化到O(n²)(每次复制元素的成本累积)。

二、为什么选择 "翻倍扩容"(2 * _capacity)?

这是一种避免频繁扩容的优化策略:

  • 每次扩容时直接将容量翻倍,能保证后续多次添加元素都不需要再次扩容
  • 从数学上可以证明,这种策略能让单次添加元素的平均时间复杂度降为O(1)( amortized O(1))

例如:

  • 初始容量为 1,添加 1 个元素后扩容到 2
  • 再添加 1 个元素(总 2 个),下次添加时扩容到 4
  • 再添加 2 个元素(总 4 个),下次添加时扩容到 8
  • 以此类推,每扩容一次,能支持的新增元素数量也翻倍

这种 "批量扩容" 的思路,用少量的空间冗余换取了时间效率的极大提升。

三、为什么还要考虑 "_size + len"?

当一次性添加大量元素(len很大)时,如果固执地用 "翻倍扩容" 可能导致空间浪费

  • 假设当前容量_capacity=100,已存储_size=50个元素
  • 现在要一次性添加len=200个元素,此时_size + len = 250
  • 如果按翻倍扩容(2*100=200),容量仍然不够,还需要再次扩容
  • 因此直接扩容到_size + len(250),既满足需求又避免不必要的空间浪费

这是一种 "按需扩容" 的补充策略,防止在批量添加元素时出现 "扩容不足" 或 "过度扩容" 的问题。

四、代码本质

  • 小规模添加元素时,用 "翻倍扩容" 减少扩容次数,优化时间效率。
  • 大规模添加元素时,用 "按需扩容" 确保刚好够用,优化空间效率。
http://www.lryc.cn/news/622553.html

相关文章:

  • AMD Ryzen AI Max+ 395四机并联:大语言模型集群推理深度测试
  • 开源 Arkts 鸿蒙应用 开发(十八)通讯--Ble低功耗蓝牙服务器
  • 昇腾AI自学Day2-- 深度学习基础工具与数学
  • 利用cursor+MCP实现浏览器自动化释放双手
  • vscode中使用CMake Tools生成compile_commands.json文件后,如何告诉clangd这个文件在哪里呢?
  • 新手向:Python列表、元组、集合和字典的用法对比
  • JavaScript 核心语法与实战笔记:从基础到面试高频题
  • macOS 中查看当前生效 shell 及配置文件的方法
  • linux网络基础
  • 二叉树的三种遍历方法
  • KVM虚拟化技术解析:从企业应用到个人创新的开源力量
  • 开源 Arkts 鸿蒙应用 开发(十七)通讯--http多文件下载
  • 4.6 Vue 3 中的模板引用 (Template Refs)
  • Vue中的数据渲染【4】
  • java 面试八股集锦
  • IO流-打印流
  • ROS相关的ubuntu基础教程
  • 移动互联网发展战略
  • Android面试指南(一)
  • C#WPF实战出真汁08--【消费开单】--餐桌面板展示
  • C#WPF实战出真汁09--【消费开单】--选择菜品
  • Linux软件编程--线程
  • socket编程UDP
  • 深度解析和鲸社区热门项目:电商双 11 美妆数据分析的细节与价值
  • AI Agents 2025年十大战略科技趋势
  • 【Java学习】锁、线程死锁、线程安全2
  • 【原理】C# 字段、属性对比及其底层实现
  • 使用npm/pnpm自身安装指定版本的pnpm
  • pnpm(Performant npm)的安装
  • Docker之安装部署——(1)配置国内docker镜像源