因此在课堂上我们必须创建一个从文件中获取单词的代码,忽略标点符号并打印出单词。不仅如此,它还必须忽略同一个单词的副本,但要记录哪些单词重复并将其计数添加到并行数组。但是我一直在程序结束时崩溃,我是否错误地删除了?
#include <fstream>
#include <iostream>
#include <cstring>
using std::cout;
using std::cin;
using std::endl;
using std::ifstream;
int GetCount(char filename[50]);
int main()
{
char filename[50] = "b.txt";
int choice = 0;
cout << "Input the file name: ";
//cin >> filename;
int numberOfWords = GetCount(filename);
cout << endl << numberOfWords << endl;
ifstream fileRead;
cin.clear();
cin.ignore(cin.rdbuf()->in_avail());
fileRead.open(filename);
if (!fileRead.is_open())
{
std::cerr << "\n Error opening file\n";
}
else
{
//Buffers to get words from file
char buffer[1000];
char bufferBuffer[1000];
我在这里声明了导致删除问题的数组
//Array of pointers to words
char ** cStringArray = new char *[numberOfWords];
*cStringArray = nullptr;
int add = 1; //Integer in case a word is repeated not to add
//Parrallel Array to integers
int * intPtr = new int;
*intPtr = 0;
//Pointers used to check for repeated words
int * startIntPtr = intPtr;
int * checkIntPtr = startIntPtr;
char ** startCStringArray = cStringArray;
char ** checkCStringArray = cStringArray;
//Index of Current Word
int indexOfWord = 0;
//Variables for character check
int i = 0;
int k = 0;
//Loop to get words from file
while (fileRead >> buffer)
{
//Add Word
add = 1;
//Copy only alpha characters
i = 0;
k = 0;
while (buffer[k] != '\0')
{
if (isalpha(buffer[k]))
{
bufferBuffer[i] = buffer[k];
i++;
}
k++;
}
bufferBuffer[i] = '\0';
strcpy(buffer, bufferBuffer);
//Actually set it in array
*cStringArray = new char[strlen(buffer) + 1];
strcpy(*cStringArray, buffer);
//Compare Against all other cstrings
for (int ii = 0; ii < indexOfWord; ii++)
{
if (strcmp(*checkCStringArray, buffer) == 0)
{
*checkIntPtr += 1;
add = 0;
}
checkCStringArray++;
checkIntPtr++;
}
//Reset Checks
checkIntPtr = startIntPtr;
checkCStringArray = startCStringArray;
//Move onto next space of cStringArray
if (add == 1)
{
cStringArray++;
*cStringArray = nullptr;
//Add one to index
indexOfWord += 1;
//Add one to intPtr
*intPtr += 1;
intPtr++;
*intPtr = 0;
}
else
{
*cStringArray = nullptr;
*intPtr = 0;
}
}
cStringArray = startCStringArray;
for (int i = 0; i < indexOfWord; i++)
{
cout << *cStringArray << endl;
cStringArray++;
}
cStringArray = startCStringArray;
intPtr = startIntPtr;
for (int i = 0; i < indexOfWord + 1; i++)
{
cStringArray[i] = nullptr;
delete[] cStringArray[i];
}
cStringArray = startCStringArray;
在这一行打破
delete [] cStringArray;
/*delete[] intPtr;*/
}
return 0;
}
答案 0 :(得分:4)
每个new
必须与delete
配对。我们来检查一下吗?
char ** cStringArray = new char *[numberOfWords];
与
配对delete [] cStringArray;
Groovy的。
*cStringArray = new char[strlen(buffer) + 1];
与
配对delete[] cStringArray[i];
一切看起来都不错。
除了......
让我们看看最后一个有更多背景的人。
for (int i = 0; i < indexOfWord + 1; i++)
{
cStringArray[i] = nullptr;
delete[] cStringArray[i];
}
Hmmmm。将指针设置为nullptr
。删除nullptr
。在删除之前,程序丢失了指针并泄漏了内存。
近距离观察不太好,周围噪音较少。
请注意,这只是查看删除。我还没有看到代码中可能存在的其他问题。乍一看,它似乎过于复杂。这就是Minimal, Complete, and Verifiable example如此有用的原因。如果你把所有不必要的东西都砍掉了,那就会让错误更加突出。