当前位置:  开发笔记 > 编程语言 > 正文

如何在C++中正确使用动态分配的多维数组

如何解决《如何在C++中正确使用动态分配的多维数组》经验,为你挑选了1个好方法。

如何在C++中定义动态多维数组?例如,二维数组?我尝试使用指针指针,但不知怎的,它失败了.



1> SergeyA..:

首先应该意识到C++中没有多维数组支持,无论是作为语言功能还是标准库.因此,我们可以做的任何事情都是对它的一些模仿.我们怎样才能模仿二维整数数组呢?这里有不同的选择,从最不适合到最合适.

尝试不当#1.使用指针指针

如果使用指向该类型的指针模拟数组,那么应该使用指向该类型的指针来模拟二维数组吗?像这样的东西?

int** dd_array = new int[x][y];

那是一个编译器错误.没有new [][]运算符,所以编译器很乐意拒绝.好吧,那怎么样?

int** dd_array = new int*[x];
dd_array[0][0] = 42;

编译.在执行时,它会因令人不快的消息而崩溃.出了点问题,但是什么?当然!我们确实为第一个指针分配了内存 - 它现在指向一个内存块,它包含指向int的x指针.但我们从未初步化过这些指针!我们再试一次吧.

int** dd_array = new int*[x];
for (std::size_t i = 0; i < x; ++i)
   dd_array[i] = new int[y];

dd_array[0][0] = 42;

这不会产生任何编译错误,并且程序在执行时不会崩溃.任务完成?没那么快.记住,每次我们打电话给new,我们都必须打电话给delete.所以,你走了:

for (std::size_t i = 0; i < x; ++i)
    delete dd_array[i];
delete dd_array;

现在,那太可怕了.语法很丑,并且手动管理所有这些指针......不.让我们全力以赴,做一些更好的事情.

减少不正当的尝试#2.使用std::vectorstd::vector

好.我们知道在C++中我们不应该真正使用手动内存管理,这里有一个方便的说法std::vector.那么,我们可以做到这一点吗?

std::vector > dd_array;

显然,这还不够 - 我们从未指定过这些数组的大小.所以,我们需要这样的东西:

std::vector > dd_array(x);
for(auto&& inner : dd_array)
    inner.resize(y);

dd_array[0][0] = 42;

那么,现在好吗?没那么多.首先,我们仍然有这个循环,它是一个痛苦的眼睛.更重要的是,我们严重损害了我们的应用程序的性能.由于每个单独的内部向量都是独立分配的,所以循环如下:

int sum = 0;
for (auto&& inner : dd_array)
    for (auto&& data : inner)
       sum += data;

将导致迭代多个独立分配的内部向量.由于CPU只会缓存连续内存,因此不能完全缓存那些小的独立向量.当你无法缓存时会伤害性能!

那么,我们该怎么做呢?

正确的尝试#3 - 单维!

我们根本就没有!当情境需要二维向量时,我们只是以编程方式使用一维向量并使用偏移量访问它的元素!这是我们的做法:

vector dd_array(x * y);
dd_array[k * x + j] = 42; // equilavent of 2d dd_array[k][j]

这给了我们精彩的语法,表现和所有的荣耀.为了让我们的生活稍微好一些,我们甚至可以在一维矢量上构建一个适配器 - 但这是留给家庭作业的.


Upvoted,但值得添加更合适的尝试4:将1D数组包装在一个对象中,以减少索引数学中的拼写错误的几率,当它在其他地方工作时,在一个地方吸引你.
在正常情况下,是的,但是对于像这样的自我回答的问题,我会包含一个非常基本的完整性包装器.除非你计划续集:Dude,哪里是我的'运营商[] []`?
推荐阅读
pan2502851807
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有