C++ 数组包装器损坏堆
续集: 项目:C++ 数组包装器损坏堆,c++,arrays,heap,dynamic-arrays,heap-corruption,C++,Arrays,Heap,Dynamic Arrays,Heap Corruption,续集: 项目: template<class T> class dyn_arr { public: dyn_arr(void) { this->array = {}; this->element_count = {}; } ~dyn_arr(void) { this->dealloc(); } bool alloc(unsigned int
template<class T> class dyn_arr
{
public:
dyn_arr(void)
{
this->array = {};
this->element_count = {};
}
~dyn_arr(void)
{
this->dealloc();
}
bool alloc(unsigned int element_count)
{
if (0 == element_count)
{
element_count = 1;
}
if (this->array != nullptr)
{
T* temp = new T[this->element_count];
if (false == this->_tempcpy(&this->array, &temp, this->element_count))
{
return false;
}
delete[] this->array;
this->array = new T[this->element_count];
if (false == this->_tempcpy(&temp, &this->array, this->element_count))
{
return false;
}
delete[] temp;
if (nullptr != this->array)
{
return true;
}
}
else
{
this->array = new T[this->element_count];
if (nullptr != this->array)
{
return true;
}
}
return false;
}
bool dealloc(void)
{
if (nullptr == this->array)
{
return false;
}
delete[] this->array;
return true;
}
bool add(T Object)
{
if (0 == Object)
{
return false;
}
if (true == this->alloc(this->element_count))
{
this->array[this->element_count] = Object;
++this->element_count;
return true;
}
return false;
}
T get(unsigned int index)
{
if (index > this->element_count)
{
return T{};
}
return this->array[index];
}
unsigned int get_count(void)
{
return this->element_count;
}
private:
bool _tempcpy(T** src, T** dest, unsigned int count)
{
if ((nullptr == src) || (nullptr == dest) || (0 == count))
{
return false;
}
for (unsigned int i = 0; i < count; ++i)
{
*dest[i] = *src[i];
}
return true;
}
T* array;
unsigned int element_count;
};
int main()
{
dyn_arr<int> pNr = {};
pNr.add(1);
pNr.add(2);
pNr.add(3);
for (int i = 0; i < pNr.get_count(); ++i)
{
printf("%d\n", pNr.get(i));
}
getchar();
return 0;
}
我正在做一个std::vector
替换
错误:
template<class T> class dyn_arr
{
public:
dyn_arr(void)
{
this->array = {};
this->element_count = {};
}
~dyn_arr(void)
{
this->dealloc();
}
bool alloc(unsigned int element_count)
{
if (0 == element_count)
{
element_count = 1;
}
if (this->array != nullptr)
{
T* temp = new T[this->element_count];
if (false == this->_tempcpy(&this->array, &temp, this->element_count))
{
return false;
}
delete[] this->array;
this->array = new T[this->element_count];
if (false == this->_tempcpy(&temp, &this->array, this->element_count))
{
return false;
}
delete[] temp;
if (nullptr != this->array)
{
return true;
}
}
else
{
this->array = new T[this->element_count];
if (nullptr != this->array)
{
return true;
}
}
return false;
}
bool dealloc(void)
{
if (nullptr == this->array)
{
return false;
}
delete[] this->array;
return true;
}
bool add(T Object)
{
if (0 == Object)
{
return false;
}
if (true == this->alloc(this->element_count))
{
this->array[this->element_count] = Object;
++this->element_count;
return true;
}
return false;
}
T get(unsigned int index)
{
if (index > this->element_count)
{
return T{};
}
return this->array[index];
}
unsigned int get_count(void)
{
return this->element_count;
}
private:
bool _tempcpy(T** src, T** dest, unsigned int count)
{
if ((nullptr == src) || (nullptr == dest) || (0 == count))
{
return false;
}
for (unsigned int i = 0; i < count; ++i)
{
*dest[i] = *src[i];
}
return true;
}
T* array;
unsigned int element_count;
};
int main()
{
dyn_arr<int> pNr = {};
pNr.add(1);
pNr.add(2);
pNr.add(3);
for (int i = 0; i < pNr.get_count(); ++i)
{
printf("%d\n", pNr.get(i));
}
getchar();
return 0;
}
每当我试图删除我正在创建的临时数组,以便存储我删除的另一个数组的复制元素,以便在调整数组大小时重新分配它时,我都会收到堆损坏错误。(如果我试图将一个数组分配给另一个数组,我实际上会将指向该数组的指针分配给另一个数组,而不是复制元素。真是疯狂的事情)
我在网上读到,这个错误实际上可能来自我实际与数组交互的部分,但只有当我尝试删除它时,错误才会弹出
我与数组交互的地方是函数\u tempcpy
。我传递一个指向源和目标数组的指针,并将每个元素从源复制到目标。我努力确保数组从0开始,而不是从1开始。在这个过程中,我对元素\u count
成员做了太多的修改,所以可能是因为我写的东西有点越界,我一直盯着代码看,看不到问题所在
代码:
template<class T> class dyn_arr
{
public:
dyn_arr(void)
{
this->array = {};
this->element_count = {};
}
~dyn_arr(void)
{
this->dealloc();
}
bool alloc(unsigned int element_count)
{
if (0 == element_count)
{
element_count = 1;
}
if (this->array != nullptr)
{
T* temp = new T[this->element_count];
if (false == this->_tempcpy(&this->array, &temp, this->element_count))
{
return false;
}
delete[] this->array;
this->array = new T[this->element_count];
if (false == this->_tempcpy(&temp, &this->array, this->element_count))
{
return false;
}
delete[] temp;
if (nullptr != this->array)
{
return true;
}
}
else
{
this->array = new T[this->element_count];
if (nullptr != this->array)
{
return true;
}
}
return false;
}
bool dealloc(void)
{
if (nullptr == this->array)
{
return false;
}
delete[] this->array;
return true;
}
bool add(T Object)
{
if (0 == Object)
{
return false;
}
if (true == this->alloc(this->element_count))
{
this->array[this->element_count] = Object;
++this->element_count;
return true;
}
return false;
}
T get(unsigned int index)
{
if (index > this->element_count)
{
return T{};
}
return this->array[index];
}
unsigned int get_count(void)
{
return this->element_count;
}
private:
bool _tempcpy(T** src, T** dest, unsigned int count)
{
if ((nullptr == src) || (nullptr == dest) || (0 == count))
{
return false;
}
for (unsigned int i = 0; i < count; ++i)
{
*dest[i] = *src[i];
}
return true;
}
T* array;
unsigned int element_count;
};
int main()
{
dyn_arr<int> pNr = {};
pNr.add(1);
pNr.add(2);
pNr.add(3);
for (int i = 0; i < pNr.get_count(); ++i)
{
printf("%d\n", pNr.get(i));
}
getchar();
return 0;
}
模板类动态
{
公众:
dyn_arr(无效)
{
这个->数组={};
该->元素计数={};
}
~dyn_arr(无效)
{
这->解除锁定();
}
bool alloc(无符号整数元素计数)
{
if(0==元素计数)
{
元素计数=1;
}
如果(此->数组!=nullptr)
{
T*temp=newt[this->element_count];
if(false==this->\u tempcpy(&this->array,&temp,this->element\u count))
{
返回false;
}
删除[]此->数组;
this->array=newt[this->element_count];
if(false==this->\u tempcpy(&temp,&this->array,this->element\u count))
{
返回false;
}
删除[]临时;
if(nullptr!=此->数组)
{
返回true;
}
}
其他的
{
this->array=newt[this->element_count];
if(nullptr!=此->数组)
{
返回true;
}
}
返回false;
}
bool DEALOC(无效)
{
if(nullptr==此->数组)
{
返回false;
}
删除[]此->数组;
返回true;
}
布尔加法(T对象)
{
if(0==对象)
{
返回false;
}
if(true==此->分配(此->元素计数))
{
this->array[this->element\u count]=对象;
++此->元素计数;
返回true;
}
返回false;
}
T get(无符号整数索引)
{
如果(索引>此->元素计数)
{
返回T{};
}
返回此->数组[索引];
}
无符号整数get_计数(void)
{
返回此->元素\u计数;
}
私人:
bool_tempcpy(T**src,T**dest,无符号整数计数)
{
if((nullptr==src)| |(nullptr==dest)| |(0==count))
{
返回false;
}
for(无符号整数i=0;i
在alloc
函数中存在一些问题,例如:
if (0 == element_count)
{
element_count = 1;
}
这是不必要的。相反,您可以在需要时执行+1
,这几乎是除temp
动态数组之外的所有位置
bool alloc(...)
{
this->array = new T[this->element_count];
//...
else
{
this->array = new T[this->element_count];
}
}
应该是
this->array = new T[this->element_count + 1];
//...
else
{
this->array = new T[this->element_count + 1];
}
这将解决分配问题。这就给我们留下了\u tempcpy()
,它失败了,因为它没有尝试获取底层数组的下一个元素,而是尝试使用双ptr本身来实现。了解运算符优先规则。固定版本:
bool _tempcpy(T** src, T** dest, unsigned int count)
{
//....
for (unsigned int i = 0; i < count; ++i)
{
(*dest)[i] = (*src)[i];
}
//....
}
同样的道理也可以应用到课堂的其他部分
此外,在C中++
dyn_arr(void)
我们不这样做。无需显式写入void
。根据C++标准:
8.3.5功能[dcl.fct]
...
由一个非依赖类型的未命名参数组成的参数列表相当于一个空参数列表
有什么特别的原因可以让你用vector的替代品来重新发明轮子吗?我想了解更多信息,对它的工作方式有更多的控制权,我只想通过编写
if(nullptr==this->array){return false;}delete[]this->array代码>-如果
块是无意义的,则整个<代码>删除[]空PTR
是一个noop-保证什么都不做。这不是你问题的原因(现在),但请看。为什么到处都是显式的这个->
?你不需要它,它让代码更难读。该死的家伙。我疯狂地不断更改代码中的内容,只修复了2个,就成功了。疯狂的狗屎。。。谢谢。我已经把双ptr改成了单指针,因为你是对的,它没有意义,也没有用。您还建议我对参数使用const,这正是我在没有参数的函数中写入void的原因。对于这两个更改,我必须花费大约30分钟的时间。在函数参数中写入<代码>空洞是C,而不是C++。写它是多余的。这是一种奉献,兄弟。当我展开包装器时,我会记住你的建议,现在它终于可以工作了!