C++ 怎么定义二维数组 C++ 动态分配二维数组的两种写法【内存】

发布时间 - 2026-02-03 00:00:00    点击率:
推荐用new分配连续内存的二维数组:先new int[rowscols]获数据区,再new int[rows]建行指针,循环设arr[i]=data+i*cols;释放时先delete

[] data后delete[] arr;非连续方式需逐行new并遍历delete[],易泄漏。

用 new 分配连续内存的二维数组(推荐)

这种写法本质是申请一块连续内存,再用指针偏移模拟二维访问,内存局部性好、释放只需一次 delete[],适合行数列数在运行时确定但固定不变的场景。

常见错误是把 int** arr 和连续内存混用,导致越界或释放崩溃。

  • 先分配一行数据的总空间:int* data = new int[rows * cols];
  • 再分配行指针数组,每行指向对应起始位置:int** arr = new int*[rows];,然后循环赋值 arr[i] = data + i * cols;
  • 使用时仍是 arr[i][j],但底层是线性地址 data[i * cols + j]
  • 释放顺序必须是:先 delete[] data;,再 delete[] arr;(不能反过来,也不能只删一个)

用 new 分配非连续内存的二维数组(不推荐但常见)

逐行 new int[cols],每行内存可能分散在堆不同位置。容易写出,但缓存不友好、释放麻烦、易漏删某一行。

典型错误是只调用 delete[] arr; 而忘记遍历删除每行,造成严重内存泄漏。

  • 先分配行指针数组:int** arr = new int*[rows];
  • 再对每行单独分配:for (int i = 0; i
  • 释放必须严格两步:for (int i = 0; i ,然后 delete[] arr;
  • 如果某次 new int[cols] 抛异常,已有行需手动回滚释放,否则泄漏

为什么 vector> 不算“动态二维数组”的等价替代?

它确实是更安全的选择,但行为上不是二维数组——vector> 的每行是独立分配的,内存不连续,且 resize() 可能触发整行拷贝;而 C 风格二维数组强调的是“一块内存+双重下标访问”语义。

如果你需要传递给 C 接口(如 OpenGL、FFmpeg),或做高性能数值计算(如矩阵乘法),vector> 无法直接传 int**int*,必须额外拷贝或重构。

  • vector>&v[0][0] 仅在首行非空时有效,且仅保证该行连续
  • 要获得连续内存,得用单维 vector + 手动索引:v[i * cols + j]
  • 没有 int** 等价物,无法满足要求二级指针的旧 API

new 分配失败时怎么处理?

C++11 起默认 newstd::bad_alloc,不会返回 nullptr。想用 nullptr 检查,得显式加 std::nothrow

连续内存分配失败风险更高(大块内存难找),非连续方式可能某一行失败而前面已成功,状态不一致。

  • int* data = new (std::nothrow) int[rows * cols];,检查 if (!data) { /* 处理 */ }
  • 非连续方式中,若第 knew int[cols] 失败,前 k 行需立即释放,否则泄漏
  • 更稳妥的做法是封装成 RAII 类,或直接用 std::unique_ptr 管理(如 std::unique_ptr data + std::unique_ptr arr

实际项目里,除非对接 C 接口或有极致性能要求,否则优先用 std::vector<:vector>> 或单维 std::vector 加索引计算;真要用 new,第一种连续内存写法更可控,但所有手动内存管理都绕不开“分配-使用-释放”三步的精确匹配。


# ai  # c++  # 为什么  # if  # for  # 封装  # int  # 循环  # 指针  # 接口  #   # delete  # 重构  # ffmpeg  # 遍历  # 的是  # 如果你  # 已有  # 只需  # 更高  # 仍是  # 要用  # 不开  # 再用 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: 如何在腾讯云服务器快速搭建个人网站?  如何在建站之星网店版论坛获取技术支持?  敲碗10年!Mac系列传将迎来「触控与联网」双革新  微信小程序 HTTPS报错整理常见问题及解决方案  Laravel如何使用缓存系统提升性能_Laravel缓存驱动和应用优化方案  JavaScript中的标签模板是什么_它如何扩展字符串功能  linux top下的 minerd 木马清除方法  iOS UIView常见属性方法小结  Laravel如何监控和管理失败的队列任务_Laravel失败任务处理与监控  Laravel如何实现本地化和多语言支持_Laravel多语言配置与翻译文件管理  Laravel如何获取当前用户信息_Laravel Auth门面获取用户ID  如何在阿里云高效完成企业建站全流程?  JavaScript如何操作视频_媒体API怎么控制播放  Laravel N+1查询问题如何解决_Eloquent预加载(Eager Loading)优化数据库查询  高配服务器限时抢购:企业级配置与回收服务一站式优惠方案  如何在香港免费服务器上快速搭建网站?  通义万相免费版怎么用_通义万相免费版使用方法详细指南【教程】  如何撰写建站申请书?关键要点有哪些?  做企业网站制作流程,企业网站制作基本流程有哪些?  猎豹浏览器开发者工具怎么打开 猎豹浏览器F12调试工具使用【前端必备】  uc浏览器二维码扫描入口_uc浏览器扫码功能使用地址  如何快速搭建安全的FTP站点?  百度浏览器ai对话怎么关 百度浏览器ai聊天窗口隐藏  手机软键盘弹出时影响布局的解决方法  Java类加载基本过程详细介绍  Win11应用商店下载慢怎么办 Win11更改DNS提速下载【修复】  Win11怎么设置虚拟桌面 Win11新建多桌面切换操作【技巧】  Laravel如何实现用户角色和权限系统_Laravel角色权限管理机制  HTML5空格和margin有啥区别_空格与外边距的使用场景【说明】  ,在苏州找工作,上哪个网站比较好?  如何正确下载安装西数主机建站助手?  高端智能建站公司优选:品牌定制与SEO优化一站式服务  如何将凡科建站内容保存为本地文件?  C++用Dijkstra(迪杰斯特拉)算法求最短路径  js代码实现下拉菜单【推荐】  Laravel如何将应用部署到生产服务器_Laravel生产环境部署流程  悟空识字怎么关闭自动续费_悟空识字取消会员自动扣费步骤  阿里云高弹*务器配置方案|支持分布式架构与多节点部署  php后缀怎么变mp4格式错误_修改扩展名提示格式不对怎么办【技巧】  如何登录建站主机?访问步骤全解析  googleplay官方入口在哪里_Google Play官方商店快速入口指南  Android利用动画实现背景逐渐变暗  Laravel中Service Container是做什么的_Laravel服务容器与依赖注入核心概念解析  瓜子二手车官方网站在线入口 瓜子二手车网页版官网通道入口  网站设计制作书签怎么做,怎样将网页添加到书签/主页书签/桌面?  作用域操作符会触发自动加载吗_php类自动加载机制与::调用【教程】  php json中文编码为null的解决办法  如何在Windows环境下新建FTP站点并设置权限?  Laravel如何使用模型观察者?(Observer代码示例)  HTML5打空格有哪些误区_新手常犯的空格使用错误【技巧】