赞
踩
单链表是线性表的链式存取结构;是用一组地址任意的存储单元存放线性表中的数据元素。链表中的数据是以结点来表示的;
结点结构:
申请新的结点:s = new Node<int> ;
当对单链表的表首元素进行删除或插入操作时,要进行区别处理,无头结点的单链表进行头指针的更新。(对表头特殊处理)
带头结点的单链表,无论单链表是否为空链表,头指针都指向头结点。不带头结点的单链表,当单链表为非空链表时,头指针指向链表第一个结点(head),当单链表为空链表时,头指针指向空(NULL)。
- //创建结点
- template<classT>
- struct Node {
- T data;
- Node<T> *next;
- };
- template<classT>
- class LinkList
- {
- Node<T> *first,*rear,*p,*s,*q; //一般情况头指针用*first
- // 带结点单链表中头结点用*head
- public:
- LinkList();
- LinkList(Ta[], intn);
- ~LinkList();
- int Length(); //求链表长度
- T Get(intpos); //按值查找
- void Insert(inti, Titem);
- void HeadInsert(Ta[], intn); //头插法
- void TailInsert(Ta[], intn); //尾插法
- void Insert(inti, Titem);
- void Detele(inti);
- int CountX(Tdata);
- void PrintLinkList(); //遍历单链表
- };
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- //头指针指向的结点为该单链表的头结点
- template<classT>
- LinkList<T>::LinkList() //无参构造函数
- {
- head=new Node<T>; //声明一个头结点
- head->next=NULL; //头结点指向的首结点为空
- }
- template<classT>
- LinkList<T>::LinkList(Ta[], intn) //有参构造函数
- {
- Node<T>*s;
- Node<T>*head=new Node<T>; //创建头结点
- rear=head;
- for (inti=0; i<n; i++) {
- s=new Node<T>; //申请新结点
- s->data=a[i];
- rear->next=s;
- rear=s;
- }
- rear->next=NULL;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- //头指针指向的结点为该单链表的首结点
- template<classT> //无参构造函数
- LinkList<T>::LinkList()
- {
- first=new Node<T>; //头指针指向新节点
- first=NULL; //首结点数据为空
- }
-
- template<classT>
- LinkList<T>::LinkList(Ta[], intn) {
- Node<T>*s=new Node<T>; //建立新结点指针
- first=s; //头指针指向新结点 s
- Node<T>*rear=first; // rear指向首结点
- for (inti=0; i<n; i++) {
- s=newNode<T>; //新结点
- s->data=a[i];
- rear->next=s; //插入 s
- rear=s; // s为尾结点
- }
- rear->next=NULL; //尾结点next设为空
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- template<classT>
- LinkList<T>::~LinkList() {
- Node<T>*rear=first; // 头指针赋值给尾结点
- while (rear) { //当结点指针不为零
- Node<T>*q=rear; // Node<T> *q = first;
- rear=rear->next; //尾指针rear 递推 , 最后rear=NULL
- deleteq;
- }
- first=NULL; //当结点指针为零 ,则为空
- }
[] 将待插入结点插在头结点的后面
- template<classT>
- LinkList<T>::~LinkList() {
- Node<T>*rear=first; // 头指针赋值给尾结点
- while (rear) { //当结点指针不为零
- Node<T>*q=rear; // Node<T> *q = first;
- rear=rear->next; //尾指针rear 递推 , 最后rear=NULL
- deleteq;
- }
- first=NULL; //当结点指针为零 ,则为空
- }
- template<classT>
- void LinkList<T>::HeadInsert(Ta[], intn) {
- head=new Node<T>;
- head->next=NULL;
- for (inti=0; i<n; i++) {
- //生成新结点
- //链接在头结点和首结点之间
- s=newNode<T>;
- s->data=a[i];
- s->next=head->next;
- head->next=s;
- }
- }
- //插入到第一个位置
- s->next=first;
- first=s;
-
- //插入到其他位置
- //rear = 插入之前的结点;
- s->next=rear->next;
- rear->next=s;
- template<classT>
- void LinkList<T>::HeadInsert(Ta[], intn) {
- for (inti=0; i<n; i++) {
- rear=first; // rear指针指向原首元结点地址first
- s=new Node<T>; //新结点 s
- s->data=a[i];
- if (i==0) {
- s->next=NULL; // 头插法数组第一个元素最终为表尾元素
- }
- else {
- s->next=rear; //在尾部加上新结点 s
- }
- first=s; // 头指针指向 s, s为首元结点 (更新头指针)
- }
- }
[将待插入结点插在终端结点的后面]
- template<classT>
- void LinkList<T>::TailInsert(Ta[], intn) {
- rear=head;
- for (inti=0; i<n; i++) {
- //生成新结点
- //链接在尾结点后面
- //尾结点后移
- s=new Node<T>;
- s->data=a[i];
- rear->next=s;
- rear=s;
- }
- rear->next=NULL;
- }
- template<classT>
- void LinkList<T>::TailInsert(Ta[], intn)
- {
- rear=first; // rear指针指向原首元结点地址first
- for (inti=0; i<n; i++) {
- s=new Node<T>; //新结点 s
- s->data=a[i];
- s->next=NULL;
- if(i==0){
- first=s ; // 如果当前是第一个元素则将头指针指向当前节点
- }
- else {
- rear->next=s; //在尾部加上新结点 s
- rear=s; // s 变为尾结点
- }
- rear=s;
- rear->next=NULL; //尾结点 next为空
- }
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
[] 在第 i个位置插入元素 item
- template<classT>
- void LinkList<T>::Insert(inti, Titem) {
- p=head;
- int j=0;
- while (p&&j<i-1) {
- p=p->next;
- j++;
- }
- if (!p||i==0) {
- cerr<<"插入位置非法。";
- exit(1);
- }
- s=newNode<T>;
- s->data=item;
- s->next=p->next;
- p->next=s;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- template<classT>
- void LinkList<T>::Insert(inti, Titem) {
- Node<T>*p=first; // p指向首元结点
- Node<T>*s=new Node<T>;
- if(i==1){ //插入第1个结点的操作
- s->data=item;
- s->next=first; //将 s放到first(首元素)前面
- first=s; //头指针指向 s (更改头指针)
- }
- else {
- intj=1; //第二个元素开始
- while (p&&j<i-1) { //找到插入元素位置的前驱结点
- p=p->next;
- j++;
- }
- if (!p||i==0) {
- cerr<<"插入位置非法。";
- exit(1);
- }
- s->data=item;
- s->next=p->next; // s->next为第 i个元素地址
- p->next=s; // 第 i-1元素 next为新元素 s
- }
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- //带头结点
- template<classT>
- int LinkList<T>::Length() {
- p=head->next; //不带头结点:p = first;
- int num=0;
- while (p) {
- p=p->next;
- num++;
- }
- return num;
- }
按位查找
- //根据位置获取元素
- template <class T>
- T LinkList<T>::Get(int pos)
- {
- p = head->next;
- int j=1;
- while(p&&j<pos) {
- p=p->next;
- j++;
- }
- if(!p||j>pos) {
- cerr<<"查找位置非法"<<endl;
- exit(1);
- }
- else {
- return p->data;
- }
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
按值查找
- //寻找某元素的位置
- template <class T>
- int LinkList<T>::Locate(T item) {
- p = head->next;
- int j=1;
- while(p&&p->data!=item) {
- p=p->next;
- j++;
- }
- if(p) {
- return j;
- }
- else {
- return 0;
- }
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- //带头结点
- template<classT>
- void LinkList<T>::PrintLinkList() {
- p=head->next; //不带头结点 p = first;
- if(!p){ //空链表
- cout<<"The LinkList is empty !"<<endl;
- }
- else{
- cout<<"LinkList: " ;
- while (p) { // p不为NULL时依次输出
- cout<<p->data ;
- if(p->next!=NULL) { cout<<","; }
- p=p->next;
- }
- }
- cout<<endl;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
- #include<iostream>
- using namespace std;
-
- template<classT>
- structNode {
- Tdata;
- Node<T>*next;
- };
- template<classT>
- class LinkList
- {
- Node<T> *head,*rear,*q,*p,*s;
- public:
- LinkList();
- LinkList(Ta[], intn);
- ~LinkList();
- int Length();
- T Get(intpos);
- int CountX(Tdata);
- void PrintLinkList();
- void HeadInsert(Ta[], intn);
- void TailInsert(Ta[], intn);
- void Insert(inti, Titem);
- void Detele(inti);
-
- };
-
- template<classT>
- LinkList<T>::LinkList()
- {
- head=new Node<T>;
- head->next=NULL;
- }
-
- template<classT>
- LinkList<T>::LinkList(Ta[], intn) {
- Node<T>*s;
- head=new Node<T>;
- rear=head;
- for (inti=0; i<n; i++) {
- s=new Node<T>;
- s->data=a[i];
- rear->next=s;
- rear=s;
- }
- rear->next=NULL;
- }
-
- template<classT>
- LinkList<T>::~LinkList() {
- p=head;
- while (p) {
- q=p;
- p=p->next;
- deleteq;
- }
- head=NULL;
- }
-
- template<classT>
- int LinkList<T>::Length() {
- p=head->next;
- int num=0;
- while (p) {
- p=p->next;
- num++;
- }
- return num;
- }
-
- template<classT>
- T LinkList<T>::Get(intpos) {
- p=head->next;
- int j=1;
- while (p&&j<pos) {
- p=p->next;
- j++;
- }
- if (!p||j>pos)
- {
- cerr<<"查找位置非法。";
- exit(1);
- }
- else return p->data;
- }
-
- template<classT>
- int LinkList<T>::CountX(Tdata) {
- int count=0;
- p=head->next;
- intj=0;
- while(p)
- {
- if(p->data==data) {
- count++;
- }
- p=p->next;
- }
- return count;
- }
-
- template<classT>
- void LinkList<T>::Insert(inti, Titem) {
- p=head;
- intj=0;
- while (p&&j<i-1) {
- p=p->next;
- j++;
- }
- if (!p||i==0) {
- cerr<<"插入位置非法。";
- exit(1);
- }
- s=new Node<T>;
- s->data=item;
- s->next=p->next;
- p->next=s;
- }
-
- template<classT>
- voidLinkList<T>::HeadInsert(Ta[], intn) {
- head=new Node<T>;
- for (inti=0; i<n; i++) {
- s=new Node<T>;
- s->data=a[i];
- s->next=head->next;
- head->next=s;
- }
- }
-
- template<classT>
- void LinkList<T>::TailInsert(Ta[], intn) {
- rear=head;
- for (inti=0; i<n; i++) {
- s=new Node<T>;
- s->data=a[i];
- rear->next=s;
- rear=s;
- }
- rear->next=NULL;
- }
-
- template<classT>
- void LinkList<T>::Detele(inti) {
- p=head;
- intj=0;
- while (p&&j<i-1) {
- p=p->next;
- j++;
- }
- if (!p||!p->next||i==0) {
- cerr<<"删除位置非法。";
- exit(1);
- }
- else
- {
- q=p->next;
- //T x = q->data;
- cout<<q->data<<endl;
- p->next=q->next;
- delete q;
- }
- }
-
- template<classT>
- void LinkList<T>::PrintLinkList() {
- p=head->next;
- if(!p){
- cout<<"The LinkList is empty !"<<endl;
- }
- else{
- cout<<"LinkList: " ;
- while (p) {
- cout<<p->data ;
- if(p->next!=NULL) { cout<<","; }
- p=p->next;
- }
- }
- cout<<endl;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
不带头结点
- #include<iostream>
- using namespace std;
-
- template<classT>
- struct Node {
- T data;
- Node<T> *next;
- };
-
- template<classT>
- class LinkList
- {
- Node<T> *first,*rear,*p,*s,*q;
- public:
- LinkList();
- LinkList(Ta[], intn);
- ~LinkList();
- int Length();
- T Get(intpos);
- int CountX(Tdata);
- void PrintLinkList();
- void HeadInsert(Ta[], intn);
- void TailInsert(Ta[], intn);
- void Insert(inti, Titem);
- void Detele(inti);
-
- };
-
- template<classT> //无参构造函数
- LinkList<T>::LinkList()
- {
- first=new Node<T>; //头指针指向新节点
- first=NULL; //新节点数据为空
- }
-
- template<classT>
- LinkList<T>::LinkList(Ta[], intn) {
- Node<T> *s=new Node<T>; //建立新结点指针
- first=s; //头指针指向新结点 s
- Node<T> *rear = first; // 头指针赋值给尾结点
- for (inti=0; i<n; i++) {
- s = new Node<T>; //新结点
- s->data=a[i];
- rear->next = s; //插入 s
- rear = s; // s为尾结点
- }
- rear->next = NULL; //尾结点next设为空
- }
-
- template<classT>
- LinkList<T>::~LinkList() {
- Node<T> *rear = first; // 头指针赋值给尾结点
- while (rear) { //当结点指针不为零
- Node<T> *q = rear; // Node<T> *q = first;
- rear = rear->next; //尾指针rear 递推 , 最后rear=0
- delete q;
- }
- first=NULL; //当结点指针为零 ,则为空
- }
-
- template<classT>
- int LinkList<T>::Length() {
- Node<T>*p = first;
- int num=0;
- while (p) {
- p=p->next;
- num++;
- }
- return num;
- }
-
- template<classT>
- T LinkList<T>::Get(intpos) {
- Node<T>*p = first;
- int j = 1;
- while (p && j<pos) { //找到第 pos的元素
- p = p->next;
- j++;
- }
- if (!p||j>pos)
- {
- cerr<<"查找位置非法。";
- exit(1);
- }
- else return p->data; //返回
- }
-
- template<classT>
- int LinkList<T>::CountX(Tdata) {
- int count=0;
- Node<T>*p = first;
- intj = 0;
- while(p)
- {
- if(p->data==data) {
- count++;
- }
- p=p->next;
- }
- return count;
- }
-
- template<classT>
- void LinkList<T>::Insert(inti, Titem) {
- Node<T>*p = first; // p指向首元结点
- Node<T>*s = new Node<T>;
- if(i==1){ //插入第1个结点的操作
- s->data = item;
- s->next = first; //将 s放到first(首元素)前面
- first = s; //头指针指向 s (更改头指针)
- }
- else {
- int j=1; //第二个元素开始
- while (p && j<i-1) { //找到插入元素位置的前驱结点
- p = p->next;
- j++;
- }
- if (!p||i==0) {
- cerr<<"插入位置非法。";
- exit(1);
- }
- s->data = item;
- s->next = p->next; // s->next为第 i个元素地址
- p->next = s; // 第 i-1元素 next为新元素 s
- }
- }
-
- template<classT>
- void LinkList<T>::HeadInsert(Ta[], intn) {
- for (inti=0; i<n; i++) {
- Node<T> *rear = first; // rear指针指向原首元结点地址first
- Node<T>*s =new Node<T>; //新结点 s
- s->data=a[i];
- if (i==0) {
- s->next=NULL; // 头插法数组第一个元素最终为表尾元素
- }
- else {
- s->next=rear; //在尾部加上新结点 s
- }
- first=s; // 头指针指向 s, s为首元结点 (更新头指针)
- }
- }
-
- template<classT>
- void LinkList<T>::TailInsert(Ta[], intn)
- {
- Node<T>*rear=first; // p指针指向原首元结点地址first
- for (inti=0; i<n; i++) {
- Node<T>*s = newNode<T>; //新结点 s
- s->data = a[i];
- s->next = NULL;
- if(i==0){
- first = s ; // 如果当前是第一个元素则将头指针指向当前节点
- }
- else {
- rear->next = s; //在尾部加上新结点 s
- rear=s; // s 变为尾结点
- }
- rear=s;
- rear->next=NULL; //尾结点 next为空
- }
- }
-
- template<classT>
- void LinkList<T>::Detele(inti) {
- if(i==1) //删除第一个结点需要更换头指针
- {
- Node<T> *q = first; // q指向第一个元素头指针指向的首元结点地址
- T x = first->data; //存放准备删除的元素
- first = q->next; //头指针指向第二个元素的地址
- delete q;
- cout<<x<<endl;
- }
- else {
- Node<T> *p = first; // p先从指向首元素开始
- int j = 1; //第二个元素开始
- while (p && j<i-1) { // p指向将删除元素 q的前驱结点
- p = p->next;
- j++;
- }
- Node<T> *q = p->next; // q指向将删除结点
- T x = q->data;
- p->next = q->next; //将*q结点从链中"断开"
- delete q;
- cout<<x<<endl;
- }
- }
-
- template<classT>
- void LinkList<T>::PrintLinkList() {
- Node<T> *p = first;
- if(!p){ //空链表
- cout<<"The LinkList is empty !"<<endl;
- }
- else{
- cout<<"LinkList: " ;
- while (p) { // p不为NULL时依次输出
- cout<<p->data ;
- if(p->next!=NULL) { cout<<","; }
- p=p->next;
- }
- }
- cout<<endl;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
LinkList.cpp
- #include<iostream>
- #include "LinkList_1.h"
- using namespace std;
- int main(){
- intmyData[] = {4,8,8,2,9,1,7,6,4,3,2,9,11,7,9};
- cout<<" — — — — > Practice One < — — — — "<<endl;
- /*利用无参构造函数建立单链表(myLinkList1) ,并打印出该单链表讯息。
- 此时,单链表中应无数据,打印出无数据的讯息。
- 在主程序中,采用 for 循环依序将数组 myData 中的数据插入单链表(myLinkList1)中,并打印出该单链表讯息。
- int myData[15] = { 4,8,8,2,9,1,7,6,4,3,2,9,11,7,9 };
- */
- LinkList<int> myLinkList_1;
- myLinkList_1.PrintLinkList();
- int myLength=sizeof(myData)/sizeof(*myData);
- cout<<"The length of input data is :"<<myLength<<endl;
- for(inti=1;i<=myLength;i++){
- myLinkList_1.Insert(i,myData[i-1]);
- }
- myLinkList_1.PrintLinkList();
-
- cout<<endl<<endl;
- LinkList<int>myLinkList_2(myData,myLength);
- cout<<" — — — — > Practice Two < — — — — "<<endl;
- /*利用有参构造函数建立单链表 ,并打印出该单链表讯息。
- int myData[15] = { 4,8,8,2,9,1,7,6,4,3,2,9,11,7,9 };
- 头插法: myLinkList2
- 尾插法: myLinkList3
- */
- cout<<"Inserting a node at the Beginning of a linked listed list ."<<endl;
- myLinkList_2.HeadInsert(myData,myLength);
- myLinkList_2.PrintLinkList();
- cout<<endl;
-
-
- cout<<"Inserting a node at the End of a linked listed list ."<<endl;
- myLinkList_2.TailInsert(myData,myLength);
- myLinkList_2.PrintLinkList();
-
- cout<<endl<<endl;
- cout<<" — — — — > Practice Three < — — — — "<<endl;
- /*
- 删除单链表中的元素
- 试写一个函数删除单链表中的结点,并返回被删除结点的内容。
- 针对 myLinkList1 中的内容进行删除。
- 删除第 1 个元素,并打印出删除元素的内容。
- 删除第 5 个元素,并打印出删除元素的内容。
- */
-
- cout<<"The data of the detele node is : " ;
- myLinkList_1.Detele(1);
- myLinkList_1.PrintLinkList();
- cout<<endl;
- cout<<"The data of the detele node is : " ;
- myLinkList_1.Detele(5);
- myLinkList_1.PrintLinkList();
-
- cout<<endl<<endl;
- cout<<" — — — — > Practice Four < — — — — "<<endl;
- /*试写一个函数計算单链表中所储存数据的个数,并返回计算的结果。
- 针对 myLinkList1 中的内容进行计算。
- 统计 9 的个数。
- */
- cout<<"The number of 9 "<<"is "<<myLinkList_1.CountX(9) <<endl;
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。