该文章主要介绍线性表的链式存储运算以及相关运算—单链表。
头文件:LinkList.h
template <typename T>
struct LinkList //单链表结点类型
{
T data; //存放数据元素
LinkList<T> *next; //指向下一个结点的域
};
template <typename T>
class LinkListClass //单链表类
{
LinkList<T> *head; //单链表头结点
public:
//=============单链表的基本运算算法===========================
LinkListClass<T>(); //构造函数,创建一个空单链表
~LinkListClass<T>(); //析构函数,销毁单链表
void CreateListF(T a[], int n); //头插法建立单链表
void CreateListR(T a[], int n); //尾插法建立单链表
void DispList(); //输出单链表所有结点值
int ListLength(); //求单链表数据结点个数
bool GetElem(int i, T &e); //求单链表中某个数据元素值
int LocateElem(T e); //按元素值查找
bool ListInsert(int i, T e); //插入数据元素
bool ListDelete(int i); //删除数据元素
void Sort(); //将单链表递增排序
//================单链表的其他运算算法=========================
template <typename C>
friend int Findlast(LinkListClass<C> &L, C x); //最后一个值为x的序号
template <typename C>
friend void Reverse(LinkListClass<C> &L); //逆置单链表
template <typename C>
friend void Combo(LinkListClass<C> &L1, LinkListClass<C> &L2, LinkListClass<C> &L3); //合并两个单链表
template <typename C>
friend void Merge2(LinkListClass<C> &L1, LinkListClass<C> &L2, LinkListClass<C> &L3); //二路归并算法合并两个单链表
};
源文件:LinkList.cpp
#include <iostream>
#include "LinkList.h"
//==================单链表的基本运算算法=====================
template <typename T>
LinkListClass<T>::LinkListClass<T>() //构造函数,创建一个空单链表
{
head = new LinkList<T>();
head->next = NULL;
}
template <typename T>
LinkListClass<T>::~LinkListClass<T>() //析构函数,销毁单链表
{
LinkList<T> *pre, *p;
pre = head;
p = pre->next;
while (p != NULL)
{
delete pre;
pre = p;
p = p->next;
}
delete pre;
}
template <typename T>
void LinkListClass<T>::CreateListF(T a[], int n)//头插法建立单链表
{
LinkList<T> *s;
int i;
head->next = NULL;
for (i = 0; i<n; i++)
{
s = new LinkList<T>();
s->data = a[i];
s->next = head->next;
head->next = s;
}
}
template <typename T>
void LinkListClass<T>::CreateListR(T a[], int n)//尾插法建立单链表
{
LinkList<T> *s, *r;
int i;
r = head;
for (i = 0; i<n; i++)
{
s = new LinkList<T>();
s->data = a[i];
r->next = s;
r = s;
}
r->next = NULL;
}
template <typename T>
void LinkListClass<T>::DispList() //输出单链表所有结点值
{
LinkList<T> *p;
p = head->next;
while (p != NULL)
{
cout << p->data << " ";
p = p->next;
}
cout << endl;
}
template <typename T>
int LinkListClass<T>::ListLength() //求单链表数据结点个数
{
int i = 0;
LinkList<T> *p;
p = head;
while (p->next != NULL)
{
i++;
p = p->next;
}
return i;
}
template <typename T>
bool LinkListClass<T>::GetElem(int i, T &e) //求单链表中某个数据元素值
{
int j = 0;
LinkList<T> *p = head;
while (j<i && p != NULL)
{
j++;
p = p->next;
}
if (p == NULL)
return false;
else
{
e = p->data;
return true;
}
}
template <typename T>
int LinkListClass<T>::LocateElem(T e) //按元素值查找
{
int i = 1;
LinkList<T> *p = head->next;
while (p != NULL && p->data != e)
{
p = p->next;
i++;
}
if (p == NULL)
return(0);
else
return(i);
}
template <typename T>
bool LinkListClass<T>::ListInsert(int i, T e)//插入数据元素
{
int j = 0;
LinkList<T> *s, *p;
if (i<1)
return false;
p = head;
while (j<i - 1 && p != NULL)
{
j++;
p = p->next;
}
if (p == NULL)
return false;
else
{
s = new LinkList<T>();
s->data = e;
s->next = p->next;
p->next = s;
return true;
}
}
template <typename T>
bool LinkListClass<T>::ListDelete(int i) //删除数据元素
{
int j = 0;
LinkList<T> *q, *p;
if (i<1)
return false;
p = head;
while (j<i - 1 && p != NULL)
{
j++;
p = p->next;
}
if (p == NULL)
return false;
else
{
q = p->next;
if (q == NULL)
return false;
p->next = q->next;
delete q;
return true;
}
}
template <typename T>
void LinkListClass<T>::Sort() //将单链表递增排序
{
LinkList<T> *p, *pre, *q;
q = head->next;
p = head->next->next;
q->next = NULL;
while (p != NULL)
{
q = p->next;
pre = head;
while (pre->next != NULL && pre->next->data<p->data)
pre = pre->next;
p->next = pre->next;
pre->next = p;
p = q;
}
}
//=========================单链表的其他运算算法================================
template <typename C>
int Findlast(LinkListClass<C> &L, C x)
{
int len = L.ListLength();
int i = 0;
int last = 0;
LinkList<C> *p = L.head->next;
while (i < len)
{
if (p->data == x)
last = i + 1;
i++;
p = p->next;
}
return last;
}
template <typename C>
void Reverse(LinkListClass<C> &L)
{
if (L.head->next == NULL)
return;
LinkList<C> *p, *q,*temp;
p = L.head->next;
q = p->next;
p->next = NULL;
while (q != NULL)
{
temp = q->next;
q->next = p;
L.head->next = q;
p = q;
q = temp;
}
}
template <typename C>
void Combo(LinkListClass<C> &L1, LinkListClass<C> &L2, LinkListClass<C> &L3)
{
LinkList<C> *p1,*p2,*p3;
LinkList<C> *s;
p1 = L1.head->next;
p2 = L2.head->next;
p3 = L3.head;
while (p1 != NULL&&p2 != NULL)
{
s = new LinkList<C>();
s->data = p1->data;
p3->next = s;
p3 = s;
p1 = p1->next;
s = new LinkList<C>();
s->data = p2->data;
p3->next = s;
p3 = s;
p2 = p2->next;
}
while (p1 != NULL)
{
s = new LinkList<C>();
s->data = p1->data;
p3->next = s;
p3 = s;
p1 = p1->next;
}
while (p2 != NULL)
{
s = new LinkList<C>();
s->data = p2->data;
p3->next = s;
p3 = s;
p2 = p2->next;
}
p3->next = NULL;
}
template <typename C>
void Merge2(LinkListClass<C> &L1, LinkListClass<C> &L2, LinkListClass<C> &L3)
{
LinkList<C> *p1, *p2, *p3;
p1 = L1.head->next;
p2 = L2.head->next;
p3 = L3.head;
L1.head->next = NULL;
L2.head->next = NULL;
while (p1 != NULL&&p2 != NULL)
{
if (p1->data < p2->data)
{
p3->next = p1;
p3 = p1;
p1 = p1->next;
}
else
{
p3->next = p2;
p3 = p2;
p2 = p2->next;
}
}
while (p1 != NULL)
{
p3->next = p1;
p3 = p1;
p1 = p1->next;
}
while (p2 != NULL)
{
p3->next = p2;
p3 = p2;
p2 = p2->next;
}
p3->next = NULL;
}
主函数:main.cpp
#include "LinkList.cpp"
using namespace std;
//=================单链表的基本运算算法========================
void main()
{
int i,e;
LinkListClass<int> L; //建立元素类型为int的单链表对象L
cout << "创建单链表L" << endl;
L.ListInsert(1,1); //插入元素1
L.ListInsert(2,3); //插入元素3
L.ListInsert(3,1); //插入元素1
L.ListInsert(4,5); //插入元素5
L.ListInsert(5,4); //插入元素4
L.ListInsert(6,2); //插入元素2
cout << "单链表L:"; L.DispList();
cout << "长度:" << L.ListLength() << endl;
//===
i=3;
L.GetElem(i,e);
cout << "第" << i << "个元素:" << e << endl;
//===
e=1;
cout << "元素" << e << "是第" << L.LocateElem(e) << "个元素\n";
//===
i=4;
cout << "删除第" << i << "个元素\n";
L.ListDelete(i);
cout << "单链表L:";L.DispList();
//===
L.Sort();
cout << "递增排序后单链表L:"; L.DispList();
cout << "销毁单链表L" << endl;
}
//==================单链表的其他运算算法=====================
void main1()
{
LinkListClass<int> L; //建立元素类型为int的单链表对象L
cout << "创建单链表L" << endl;
L.ListInsert(1, 1); //插入元素1
L.ListInsert(2, 3); //插入元素3
L.ListInsert(3, 1); //插入元素1
L.ListInsert(4, 5); //插入元素5
L.ListInsert(5, 4); //插入元素4
L.ListInsert(6, 2); //插入元素2
L.ListInsert(7, 102); //插入元素102
L.DispList();
//===
int a =5;
int last = Findlast(L, a);
cout << "最后一个值为x的序号为:"<<last << endl;
//===
Reverse(L);
cout << "逆置单链表L:"; L.DispList();
//===
int a1[3] = { 1, 2, 3 };
int a2[5] = { 4, 7, 9, 4, 6 };
LinkListClass<int>L1, L2,L3;
L1.CreateListR(a1, 3);
L2.CreateListR(a2, 5);
cout << "单链表L1:"; L1.DispList();
cout << "单链表L2:"; L2.DispList();
Combo(L1, L2, L3);
cout << "单链表L3:"; L3.DispList();
//===
int a4[3] = { 1, 2, 3 };
int a5[5] = { 4, 7, 9, 18,56 };
LinkListClass<int>L4, L5, L6;
L4.CreateListR(a4, 3);
L5.CreateListR(a5, 5);
cout << "单链表L4:"; L4.DispList();
cout << "单链表L5:"; L5.DispList();
Merge2(L4, L5, L6);
cout << "单链表L6:"; L6.DispList();
}