第一次修改, 存在内存泄露!析构函数有误,只删除了头结点,其他结点的空间并未释放,原析构函数代码保存在注释部分,更新至现有的析构代码。
#pragma once
#include<iostream>
using std::cout;
using std::endl;
template<typename T>
struct Node
{
T data;//数据域
Node* Next;//指针域,指向下一个结点
};
template<typename T>
using List = Node<T>*;//别名要放在构造体下面,list类型的参数表示头结点
template<typename T>
using Position = Node<T>*;//表示结点的指针位置
template<typename T>
class SingLinkedList
{
public:
SingLinkedList();//构造函数,创建一个头结点
~SingLinkedList();//析构函数
int Length();//求表长
const T& FindKth(int K);//按位序查找,返回值
Position<T> Find(const T& X);//按值查找,返回位置
bool Insert(const T& x, const int& i);
bool Delete(int i);
private:
List<T> L;//头结点
};
template<typename T>
SingLinkedList<T>::SingLinkedList()//创建头结点
{
L = new Node<T>;
L->Next = nullptr;
}
/*
template<typename T>
SingLinkedList<T>::~SingLinkedList()//删除头结点
{
delete L;
}
*/
template<typename T>
SingLinkedList<T>::~SingLinkedList()//删除所有结点
{
Position<T> pre;
while (L->Next != nullptr) {
pre = L->Next;
L->Next = pre->Next;
delete pre;
}
delete L;
}
template<typename T>
int SingLinkedList<T>::Length()
{
int cnt{ 0 };
//List<T> p = L->Next;//这种写法算表长的时候没有包含头结点;
List<T> p = L;//这种包含了
while (p)
{
p = p->Next;
++cnt;
}
return cnt;
}
template<typename T>
#define ERROR1 -1
const T& SingLinkedList<T>::FindKth(int K)
{//头结点后移动k次
Position<T> p;
p = L;
int cnt = 0;
while (p&&cnt<K)
{
p = p->Next;
cnt++;
}
if ((cnt == K) && p)
return p->data;
else
return ERROR1;
}
template<typename T>
#define ERROR2 nullptr
Position<T> SingLinkedList<T>::Find(const T& X)
{
Position<T> p= L->Next;//防止头结点的随机参数和X相等
while (p&&p->data != X)
p = p->Next;
if (p)
return p;
else
return ERROR2;
}
template<typename T>
bool SingLinkedList<T>::Insert(const T& x, const int& i)
{
Position<T> tmp, pre;
int cnt = 0;
/*查找位序为i-1的结点*/
pre = L;//pre指向表头
while (pre&&cnt<i-1)
{
pre = pre->Next;
++cnt;
}
if (pre == nullptr || cnt != i - 1) {
cout << "插入位置参数错误" << endl;
return false;
}
else {
tmp = new Node<T>;
tmp->data = x;
tmp->Next = pre->Next;
pre->Next = tmp;
return true;
}
}
template<typename T>
bool SingLinkedList<T>::Delete(int i)
{
Position<T> tmp, pre;
int cnt = 0;
pre = L;
while (pre&&cnt < i - 1) {
pre = pre->Next;
++cnt;
}
if (pre == nullptr || pre->Next == nullptr || cnt != i - 1) {
cout << "删除位置参数错误" << endl;
return false;
}
else {
tmp = pre->Next;
pre->Next = tmp->Next;
delete tmp;
return true;
}
}
#include"单向链表.h"
int main()
{
SingLinkedList<int> list{};
list.Insert(1, 1);
list.Insert(2, 2);
list.Insert(3, 3);
list.Insert(4, 4);
list.Insert(5, 5);
list.Insert(6, 6);
cout << list.FindKth(5) << endl;
cout << list.Find(6) << endl;
return 0;
}
这篇博客介绍了如何修正C++单向链表类的析构函数,避免内存泄漏。作者指出原来的析构函数只删除了头结点,而未释放其余结点的内存。修复后的析构函数通过迭代方式正确地释放了所有结点。此外,文章还展示了链表的其他功能,如求表长、按位序查找、按值查找、插入和删除元素的实现。
296

被折叠的 条评论
为什么被折叠?



