动态改变数组大小的问题(C++)

wangkuiyue 2007-09-18 11:56:10
假定用一维数组a [ 0:s i z e - 1 ]来存储一组元素。如果有n个元素,可以把它们存储在a [ 0 ] , . . . , a [ n - 1 ]中。当n超过s i z e时,数组将不足以存储所有元素,必须分配一个更大的数组。类似地,如果元素的数目比s i z e小很多,我们又可能希望减少数组的大小,以便释放出多余的空间为其他地方所用。要求编写一个模板函数C h a n g e S i z e 1 D把数组a的大小从s i z e变成To S i z e。函数
首先应该分配一个新的、大小为To S i z e的数组,然后把原数组a中的n个元素复制到新数组a中,最后释放原数组a所占用的空间,类似的,编写一个函数ChangeSize2D 来改变一个二维数组的大小。
我对这类东北分配释放内存的搞不太清楚,大家帮帮忙
...全文
16797 24 打赏 收藏 转发到动态 举报
写回复
用AI写文章
24 条回复
切换为时间正序
请发表友善的回复…
发表回复
众生皆苦 2011-06-01
  • 打赏
  • 举报
回复
这里只用模板函数来做,不用stl

#include <iostream>
using namespace std;



//删除二维数组
template<typename T>
void Delete2DArray(T ** &x, int rows)
{
//删除二维数组x
//释放为每一行所分配的空间
for (int i=0; i<rows; i++)
{
delete []x[i];
}

//删除行指针
delete []x;
x = NULL;
}

template<typename T>
void ChangeSize2D(T ** &arr, int row,int col, int ToRow,int ToCol)
{
T **tempArr;
tempArr = new T *[ToRow];
for (int i=0; i<ToRow; i++)
{
tempArr[i] = new T[ToCol];
}

for (int i=0; i<row; i++)
{
for (int j=0; j<col; j++)
{
tempArr[i][j] = arr[i][j];
}
}

//释放原来的二维数组的空间
Delete2DArray(arr,row);
arr = tempArr;
}

int main()
{
//这里都没有捕获异常
int **arr;
arr = new int*[3];
for (int i=0; i<3; i++)
{
arr[i] = new int[3];
}

for (int i=0;i<3;i++)
{
for (int j=0; j<3;j++)
arr[i][j] = i;
}

ChangeSize2D(arr,3,3,4,4);
arr[3][3] = 50;

//未赋值的都是乱码,但测试了一下函数没问题
for (int i=0;i<4;i++)
{
for (int j=0; j<4; j++)
cout << arr[i][j] << " ";

cout << endl;
}
return 0;
}
众生皆苦 2011-06-01
  • 打赏
  • 举报
回复
刚才的是动态调整一维数组大小的模板函数
众生皆苦 2011-06-01
  • 打赏
  • 举报
回复
#include <iostream>
#include <cassert>
using namespace std;

template <typename T>
void Changesize1D(T * &arr,int size, int ToSize)
{
T *tempArr;
tempArr= new T[ToSize];

for (int i=0; i<size; i++)
{
tempArr[i] = arr[i];
}
delete []arr;
arr = tempArr;
}

//以下为测试模板函数是否正确
int main()
{
int *arr;
arr = new int[4];
for (int i=0; i<4;i++)
{
arr[i] = i+2;
}

Changesize1D(arr,4,8);//这里可以用try..catch捕获分配内存失败的异常

arr[4] = 6;
for (int i=0; i<5; i++)
{
cout << arr[i] << " ";
}
cout << endl;
return 0;
}
fish6344 2007-09-27
  • 打赏
  • 举报
回复
那好啊,我们等等看,除了上述使用"纯体力劳动"的笨办法或使用容器模板,还有更好的办法是什么呢?
wangkuiyue 2007-09-25
  • 打赏
  • 举报
回复
我这个问题是书上的题目,我做了没做对,就问问大家的,书上不会出解决不了的问题吧
fish6344 2007-09-22
  • 打赏
  • 举报
回复
arong1234() 说“实际上这个问题本质上讲都是不可能的,其他人说的方法已经不是"数组"了。动态数组在C99之前是不支持的,而C99之后似乎也没有支持动态调整数组大小的”

此语非常正确!C风格的数组是强调效率的产物,在发挥效率到极致的同时,必然失去了今天大家都向往的弹性(古代,大家可不象今天对弹性有如此多的需求!这令开发工具的发明人们至今仍在为此伤脑精!),因而,它有其'先天'的缺陷。而对程序员动态调整C风格数组大小的需求,唯有我先前说的"纯体力劳动的笨掘的办法"!

我还是非常賛同Herb Sutter博士的建议:"尽量使用vector,不要使用数组!"(见《More Exceptional C++》条款7-结论page48)
lddLinan 2007-09-21
  • 打赏
  • 举报
回复
>>有什么不可以的。erase然后swap就是了。

...高不成低不就,狗尾续貂
arong1234 2007-09-21
  • 打赏
  • 举报
回复
楼主不停要人给出答案,写函数
实际上这个问题本质上讲都是不可能的
其他人说的方法已经不是“数组”了。动态数组在C99之前是不支持的,而C99之后似乎也没有支持动态调整数组大小的

因此单从数组尺寸角度讲,是无解的
Quebradawill 2007-09-21
  • 打赏
  • 举报
回复
楼主的题是书中的一道题,应该不象楼上说得那么复杂吧。
fish6344 2007-09-19
  • 打赏
  • 举报
回复
#include<vector>

void main()
{
//配置一个容器、为它预分配内存以及填充值:1-10:
vector<long> _vc;
_vc.reserve(10);
for(long _loop = 1; _loop <= 10;_loop++) _vc.push_back(_loop);

//此时_vc,就其内存配置以及实际使用来说,等同于一个长度为10的long数组!

//你中可以认为它是一个数组,象数组那样使用:
cout << "容器中第9个元素值: " << _vc[8] << endl;//输出:"容器中第9个元素值: 9" ;

//如果有扩在空间的需求,例如为数组增加一个值为'100的'元素,可以如下:
_vc.push_back(100);

//可以通过如下代码看到: (输出:"容器中第9个元素值:100" )
cout << "容器中第11个元素值: " << _vc[10] << endl;

//可以通过如下代码看到,_vc又等同于一个长度为11的long数组:
cout << "_vc的size: " << _vc.size() << endl;

/*
_vc较数组而言,还有更多的灵活性,如动态的插入、删除等等......
还可以使用迭代器,以提供更强大,更安全的功能........
当然,也和lddLinan(粪青多了,社会自然和谐了) 朋友说的一样:"vector不是什么都能
做......"但那极小的限制,通常我们都能够从vector及其它STL容器获得巨在的利益!

至于他又说到:"我们又可能希望减少数组的大小"的问题,我们可以如下解决:
*/

//例如我们想把_vc缩小size为5,则使用Herb Sutter博士的方法:
_vc.erase(_vc.begin() + 5,_vc.end());
vector<long>(_vc).swap(_vc);

//如下将演示出我们缩小原数组愿望的良好实现:
cout << "容器中第5个元素值: " << _vc[4] << endl;
cout << "缩小后的_vc的size: " << _vc.size() << endl;

_PAUSE;
}
lddLinan 2007-09-19
  • 打赏
  • 举报
回复
vector不是什么都能做,至少我接触的资料提到过,vector没实现“如果元素的数目比s i z e小很多,我们又可能希望减少数组的大小”
weijiangshanwww 2007-09-19
  • 打赏
  • 举报
回复
《STL源代码剖析》里面就有,配置器的实现。

应该是导师分配的作业吧?
wangkuiyue 2007-09-19
  • 打赏
  • 举报
回复
有人能写出这个函数可以吗?
iLampard 2007-09-19
  • 打赏
  • 举报
回复
vector
iambic 2007-09-19
  • 打赏
  • 举报
回复
>>vector不是什么都能做,至少我接触的资料提到过,
>>vector没实现“如果元素的数目比s i z e小很多,我们又可能希望减少数组的大小”
有什么不可以的。erase然后swap就是了。
fish6344 2007-09-19
  • 打赏
  • 举报
回复
不好意思,上面有些字打错了,现更正如下:

#include<vector>

void main()
{
//配置一个容器、为它预分配内存以及填充值:1-10:
vector<long> _vc;
_vc.reserve(10);
for(long _loop = 1; _loop <= 10;_loop++) _vc.push_back(_loop);

//此时_vc,就其内存配置以及实际使用来说,等同于一个长度为10的long数组!

//你可以认为它是一个数组,象数组那样使用:
cout << "容器中第9个元素值: " << _vc[8] << endl;//输出:"容器中第9个元素值: 9" ;

//如果有扩在空间的需求,例如为数组增加一个值为'100的'元素,可以如下:
_vc.push_back(100);

//可以通过如下代码看到: (输出:"容器中第11个元素值:100" )
cout << "容器中第11个元素值: " << _vc[10] << endl;

//可以通过如下代码看到,_vc又等同于一个长度为11的long数组:
cout << "_vc的size: " << _vc.size() << endl;

/*
_vc较数组而言,还有更多的灵活性,如动态的插入、删除等等......
还可以使用迭代器,以提供更强大,更安全的功能........
当然,也和lddLinan(粪青多了,社会自然和谐了) 朋友说的一样:"vector不是什么都能
做......"但那是极小的限制,通常我们都能够从vector及其它STL容器获得巨在的利益!

至于他又说到:"我们有可能希望减少数组的大小"的问题,我们可以如下解决:
*/

//例如我们想把_vc缩小size为5,则使用Herb Sutter博士的方法:
_vc.erase(_vc.begin() + 5,_vc.end());
vector<long>(_vc).swap(_vc);

//如下将演示出我们缩小原数组愿望的良好实现:
cout << "容器中第5个元素值: " << _vc[4] << endl;
cout << "缩小后的_vc的size: " << _vc.size() << endl;

_PAUSE;
}

xugang_2001 2007-09-18
  • 打赏
  • 举报
回复
这个也不是很难的,就是要封装一下,建议楼主看看STL方面的书籍,因为STL里面的容器大多实现了此功能。比如常见的Vector和List都是动态分配大小
ckt 2007-09-18
  • 打赏
  • 举报
回复
用vector就行了
jeffchen 2007-09-18
  • 打赏
  • 举报
回复
如果可能的话,尽量使用stl的容器,如vector、list、dqueue,而不是自己写。
fish6344 2007-09-18
  • 打赏
  • 举报
回复
动态改变数组的大小,别无它法,唯有:

在堆中new[]出一个新的数组,再从旧数组把数据搬移到新的数组,最后在删除旧的数组......
由此,可以看出这是"纯体力劳动"的笨掘的办法。

但是,动态改变数组-进一步说是动态改变线性内存空间是程序员的一个非常重要的需求,怎么来满足这一需求呢?

幸运的是,现代标准C++借助STL容器给我们提供了解决之道!

Herb Sutter博士强烈鼓励C++程序员在有上述需求时,采用标准vector模板容器类,而不要使用C风格的数组。!并在他的《More Exceptional C++》条款7中详细的向我们阐明了二点:

使用vector<>容器是安全的,而且没有效率损失!



加载更多回复(4)

65,210

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧