调用delete[]会中断我的C++程序
Calling delete[] breaks my C++ program
更新:感谢您的快速回复。我似乎发布了一个旧版本的代码。除了参数化构造函数之外,所有内容都保持不变。正如你所看到的,代码中有一些缺陷,但请记住,我还没有完全完成这项工作。目前我更担心数组,因为这是昨天引入的一个新概念。我尝试了几种不同的方法,并对此进行了数小时的研究。大多数回复都说只使用向量类,但这是家庭作业,有助于我们理解内存分配和动态数组。目前,这是我的.cpp和.h文件,它给我带来了问题。每次触发删除(或清除函数)操作时,都会出现一个错误,说明blahblah.exe已触发断点。
MyVector.h
#pragma once
class MyVector
{
private:
int arraySize;
int arrayCapacity;
int* theData;
void grow();
public:
MyVector();
MyVector(int n);
int size() const;
int capacity() const;
void clear();
void push_back(int n);
int& at(int n);
~MyVector();
};
MyVector.cpp
#include "MyVector.h"
#include <iostream>
using namespace std;
MyVector::MyVector()
{
arraySize = 0;
arrayCapacity = 0;
theData = new int[0];
}
MyVector::MyVector(int capacityIn)
{
theData = new int [capacityIn];
arraySize = 0;
arrayCapacity = 0;
}
int MyVector::size() const
{
return arraySize;
}
int MyVector::capacity() const
{
return arrayCapacity;
}
void MyVector::clear()
{
delete [] theData;
theData = nullptr;
}
void MyVector::push_back(int n)
{
if (arrayCapacity==0)
{
arrayCapacity++;
MyVector(arrayCapacity);
}
if (arraySize == arrayCapacity)
{
grow();
MyVector(arrayCapacity);
}
theData[arraySize] = n;
arraySize++;
}
int& MyVector::at(int index)
{
if (index >= 0 && index<arraySize)
{
return (theData[index]);
}
else
{
throw index;
}
}
void MyVector::grow()
{
arrayCapacity = arrayCapacity + arrayCapacity;
}
MyVector::~MyVector()
{
if (theData != nullptr)
{
clear();
}
}
我已经看到了很多问题:
- 您不应该像这样显式地调用构造函数。它不会像你想的那样。将分配放入实际成员函数中
- 每次"增长"数组时,都只是分配新的,这会导致泄漏,因为上一个指针没有被删除
- 您要问的主要问题是:您甚至没有将分配的指针存储在构造函数中。将
int* theData = new int [capacityIn];
更改为theData = new int [capacityIn];
。例如,您在第一个构造函数中做得很正确 - 您没有在第二个构造函数(
MyVector(int)
)中初始化arraySize
或arrayCapacity
Nitticks:
- 删除之前不需要检查
nullptr
- 不需要
new int[0]
。您永远不应该访问内存,所以只需将其初始化为nullptr
即可
此处:
MyVector::MyVector(int capacityIn)
{
int* theData = new int [capacityIn];
}
您声明了一个本地指针theData
,该指针遮蔽当前对象的theData
数据成员,使其未初始化。从那时起,所有的赌注都押在了使用它上,而你的程序最终崩溃的地方正是delete[]
,这纯属偶然。写入
MyVector::MyVector(int capacityIn)
{
theData = new int [capacityIn];
}
而arraySize
和arrayCapacity
也必须被初始化。
除此之外,你还会遇到
MyVector(arrayCapacity);
在CCD_ 14函数中分配类型为CCD_;它不会改变当前对象。
这会给您带来无法解决的问题:
int* theData = new int [capacityIn];
你说:"请定义一个整数指针…"等等。成员变量与你在方法中定义的变量不同;那样做毫无意义。相反,你应该这样做:
theData = new int [capacityIn];
或者,仅出于教育目的(为了让您了解我们正在分配给成员变量):
this->theData = new int [capacityIn];
此外(有些要点可能没有那么重要,但我想指出它们,因为你是一个新人):
请在第二个构造函数中设置您的其他变量,似乎您忘记了这样做。
MyVector::MyVector(int capacityIn) { theData = new int [capacityIn]; arraySize = capacityIn; arrayCapacity = capacityIn; }
你应该有有有意义的名字,
theData
是你绝对应该避免的。http://petdance.com/2012/04/the-worlds-two-worst-variable-names/- 您的方法应该以动词开头,例如
getDimension()
getCapacity()
等等 - 建设者是构造函数,这意味着每当构造或创建项时都要调用它们。您绝对不应该以任何方式显式地调用构造函数
- 这是一条基本规则:无论何时使用
new
命令访问内存,都应该在一段时间后的某个地方调用delete
。您的代码存在严重的内存泄漏
我本可以帮你更多的忙,但我并不完全理解你试图用一些方法实现什么,即grow()
和pushBack()
。
通过构造函数内部的赋值语句初始化变量不是一种好的风格。相反,应该在输入构造函数主体之前初始化变量。
可以使用成员初始值设定项列表,也可以在类定义中提供默认值。后者在这里似乎最简单:
class MyVector
{
private:
int arraySize = 0;
int arrayCapacity = 0;
int* theData = nullptr;
// ....
在构造函数中,您应该利用现有的函数来做同样的事情,而不是复制代码:
MyVector::MyVector(int capacityIn)
{
// call function which increases capacity to match capacityIn.
}
目前,您实际上没有增加容量的功能,因此需要添加一个。(grow()
函数使int变量增加,但不分配更多内存,因此这只会导致代码写入超过实际分配的空间的末尾)。
它可能看起来像:
void grow( int newCapacity )
{
if ( newCapacity < arrayCapacity )
return; // we do not need to shrink
int *newData = new int [new_capacity];
if ( arraySize > 0 )
std::copy(arrayData, arrayData + arraySize, newData);
delete[] arrayData;
newData = arrayData;
}
然后您可以修改grow()
(如果您仍然想保留它的话),并且push_back()
也可以调用此函数。
请注意,clear()
函数只需执行arraySize = 0;
即可。它不需要释放任何内存;您可以保留该容量以备将来使用。
- 我的神经网络不起作用 [XOR 问题]
- C++我的数学有什么问题,为什么我的代码不能正确循环
- 我的字符计数代码计算错误.为什么
- 为什么我的C#代码在调用回C++COM直到Task时会暂停.等待/线程.加入
- cmake在我的项目中所需的所有静态库都不成功
- 为什么我的代码在输出中增加了93天
- 我的简单if-else语句是如何无法访问的代码
- 为什么我的for循环不能正确获取argv
- 我的项目不会像"undefined reference to `grpc::g_core_codegen_interface'"那样使用未定义的引用错误进行编译
- 0-1背包代码中的错误.我的代码中有什么错误
- 当我的阵列太大时出现分段错误
- 如何确认我的constexpr表达式实际上已经在编译时执行
- 为什么二进制搜索在我的测试中不起作用
- 如何指定我希望我的LIB链接到的DLL文件?-Visual Studio 2019
- 我的代码中有错误吗?使用BGI图形的C++代码对我不起作用
- 当我在main中声明了我的2d数组时,为什么我的程序会退出
- OpenGL在启用深度测试时不会丢弃我的碎片
- 为什么我的 std::ref 无法按预期工作?
- clang整洁10忽略了我的NOLINT命令
- 为什么我的删除节点函数实际上没有删除节点?