c++ - 无效读取大小为 4 的数组的递增大小
问题描述
我在运行 Valgrind 时遇到 4 个错误,试图增加我用于模板化堆栈的数组(最初大小为 10),当我尝试向数组中添加第 11 个元素时,valgrind 给了我 4 个错误(恰好当我必须增加推动期间的尺寸):
class stack {
private:
int _size = 10;
T *_data;
int _top;
int _count = 0;
public:
// costructor used
stack(int s) {
this->_size = s;
_data = new T[_size];
this->_top = -1;
}
....
void push(T v) {
if (_count <= _size) {
this->_top++;
this->_data[_top] = v;
this->_count++;
}else{
//HEAP ERRORS HERE ++++++++
_size++;
T *temp = new T[_size];
for(int i = 0; i < _top; i++) {
temp[i] = _data[i];
}
delete [] _data;
_data=temp;
_data[_top] = v;
this->_top++;
this->_count++;
}
我不确定 else 语句之后的 new 运算符和 delete[] ,我认为我在那里遇到了问题,但我想不出另一种方法来解决它。
在 main.cpp 中,我只在模板堆栈中推送 11 个元素:
stack<int> s;
s.push(1);
s.push(2);
s.push(3);
s.push(4);
s.push(5);
s.push(6);
s.push(7);
s.push(8);
s.push(9);
s.push(10);
s.push(11);
这是 valgrind 的输出
==4178== Invalid write of size 4
==4178== at 0x10921E: stack<int>::push(int) (stack.h:85)
==4178== by 0x108ED2: main (main.cpp:32)
==4178== Address 0x5b82ca8 is 0 bytes after a block of size
40 alloc'd
==4178== at 0x4C3089F: operator new[](unsigned long) (in
/usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==4178== by 0x109144: stack<int>::stack() (stack.h:28)
==4178== by 0x108B8D: main (main.cpp:9)
HEAP SUMMARY:
==4178== in use at exit: 0 bytes in 0 blocks
==4178== total heap usage: 4 allocs, 4 frees, 73,808 bytes
allocated
==4178==
==4178== All heap blocks were freed -- no leaks are possible
==4178==
==4178== For counts of detected and suppressed errors, rerun with: -v
==4178== ERROR SUMMARY: 4 errors from 4 contexts (suppressed: 0 from
0)
谢谢你。
解决方案
正如 Dave S 所提到的,这种if (_count <= _size)
情况正在导致您的堆损坏。将条件更改为if (_count < _size)
将导致您期望的行为。
实际上,您将从 0 迭代到 10,在触发溢出之前总共推送 11 次。
推荐阅读
- xamarin - 如何在 xamarin 表单中创建带有或不带有 Web 视图的富文本框?
- python - 如何修复 - 没有这样的表:main.auth_user__old
- django - base.css 没有被导入页面?
- java - 在 Cucumber 中存储 REST API 响应的最佳方式是什么
- postgresql - 如何在本地使用 kafka 从 aws rds postgresql 中提取数据?
- http - 如何重构这个基类并拆分它的功能?
- javascript - JavaScript-在for循环中获取值的总和
- c# - 编写日志消息并在 Perfview 中显示的最简单方法
- jquery - 如何使用新的 order 属性重新初始化我的 jquery 数据表,同时保持我以前的其他属性不变?
- java - 使用 Apache POI 导出数据时印度(INR)和美国(美元)的货币格式不起作用