C++数据结构之传统单链表

  这几天有空重写一下数据结构,从单链表开始吧,这个是C++版本的,后面会根据情况是否补充上C版本的。

这个文章写了之后,也查看了网络上其他的数据结构写法,发现大家的写法多多少少都有一些不一样的地方,而

我的写法也和大家多多少少有一些不一样的地方,欢迎大家参阅,如果有问题请帮忙指正,我会尽力修改,希望

大家能够一起进步!谢谢!

LinkList.h头文件

 1 #pragma once
 2 #include<iostream>
 3 using namespace std;
 4 
 5 class LinkNode
 6 {
 7 public:
 8     int data;
 9     LinkNode* next;
10 };
11 
12 class LinkList
13 {
14 public:
15     LinkList();
16 
17     //插入操作
18     void InsertLinkNodeByPox(int pox, int val);
19 
20     //根据值删除元素
21     void RemoveLinkNodeByVal(int val);
22 
23     //根据位置删除元素
24     void RemoveLinkNodeByPox(int pox);
25 
26     //反转链表  方法1 这个是我第一时候写的,方法比表原始,本来准备删除的,不过毕竟是心血,还是放上面把。。。。。。  较笨拙,不推荐。。
27     void reverse();
28 
29     //反转链表  方法1  这个简单  非递归方法
30     void reverseSimply();  //方法简单!
31 
32     //递归实现链表反转
33     LinkNode* reserveByRecursion(LinkNode* hd);
34 
35     //遍历链表
36     void ForEachLinkList();
37 
38     //根据值查找节点的位置
39     LinkNode* FindVal(int val);
40 
41     //返回长度
42     int LinkListLength();
43 
44 
45     //清空链表
46     void clearList();
47 
48     //析构函数
49     ~LinkList();
50     
51 public:
52     LinkNode* head;
53 
54     int length;
55 };

 

LinkList.cpp实现文件

 

  1 #include "LinkList.h"
  2 
  3 LinkList::LinkList()
  4 {
  5     this->length = 0;
  6     this->head = new LinkNode;
  7     head->data = -1;
  8     head->next = NULL;
  9 }
 10 
 11 void LinkList::InsertLinkNodeByPox(int pox, int val)
 12 {
 13     if (pox < 0 || pox > this->length)
 14     {
 15         pox = this->length;
 16     }
 17     
 18     LinkNode* pcurNode = this->head;
 19 
 20     //找到插入位置的前一个节点
 21     for (int i = 0; i < pox; ++i)
 22     {
 23         pcurNode = pcurNode->next;
 24     }
 25     LinkNode* newNode = new LinkNode;
 26     newNode->data = val;
 27     newNode->next = pcurNode->next;
 28     pcurNode->next = newNode;
 29 
 30     this->length++;
 31 }
 32 
 33 void LinkList::RemoveLinkNodeByVal(int val)
 34 {
 35     if (this->length <= 0)
 36     {
 37         return;
 38     }
 39     LinkNode* pcurNode = this->head;
 40     LinkNode* preNode = this->head;
 41     
 42     for (int i = 0; i < this->length; ++i)
 43     {
 44         pcurNode = pcurNode->next;
 45         if (pcurNode->data == val)
 46         {
 47             preNode->next = pcurNode->next;
 48             delete pcurNode;
 49             pcurNode = NULL;
 50             this->length--;
 51             return;
 52         }
 53         preNode = pcurNode;
 54     }
 55 
 56 }
 57 
 58 void LinkList::RemoveLinkNodeByPox(int pox)
 59 {
 60     if (pox < 0 || pox >= this->length)
 61     {
 62         return;
 63     }
 64     LinkNode* pcurNode = this->head;
 65 
 66     //找到前去节点
 67     for (int i = 0; i < pox; ++i)
 68     {
 69         pcurNode = pcurNode->next;
 70     }
 71 
 72     LinkNode* delNode = pcurNode->next;
 73     pcurNode->next = delNode->next;
 74     delete delNode;
 75     delNode = NULL;
 76 
 77     this->length--;
 78 }
 79 
 80 void LinkList::reverse()
 81 {
 82     if (NULL == this->head->next)
 83     {
 84         return;
 85     }
 86     LinkNode* pFirst = this->head->next;  //指向头结点
 87 
 88     if (NULL == pFirst->next)
 89     {
 90         return;
 91     }
 92     LinkNode* pMid = this->head->next;    //指向头结点的下一个节点
 93 
 94     if (NULL == pMid->next)
 95     {
 96         pFirst->next = NULL;
 97         pMid->next = pFirst;
 98         this->head->next = pMid;
 99         return;
100     }
101 
102     LinkNode* pLast = pMid->next;
103     pFirst->next = NULL;
104     while (true)
105     {
106         pMid->next = pFirst;  //让第二个节点指向第一个节点
107         pFirst = pLast->next;  //让第一个节点挪动到最后一个节点的下一个
108         
109         if (NULL == pFirst)
110         {
111             pLast->next = pMid;
112             head->next = pLast;
113             return;
114         }
115 
116         pLast->next = pMid;
117         pMid = pFirst->next;
118 
119         if (NULL == pMid)
120         {
121             pFirst->next = pLast;
122             head->next = pFirst;
123             return;
124         }
125 
126         pFirst->next = pLast;
127         pLast = pMid->next;
128         if (NULL == pLast)
129         {
130             pMid->next = pFirst;
131             head->next = pMid;
132             return;
133         }
134     }
135 }
136 
137 void LinkList::reverseSimply()
138 {
139     LinkNode* pnext = this->head->next;  //记载下一个节点,也是反转后的第一个节点
140 
141     LinkNode* pcur = NULL;  //记载当前的
142     LinkNode* ppre = NULL;    //记载前一个节点
143 
144     while (true)
145     {
146         if (NULL == pnext || NULL == pnext->next)  //如果只有头节点或者只有一个节点,或者pnext到了最后一个节点
147         {
148             this->head->next = pnext;
149             if (pnext != NULL)             //防止只有头结点情况
150             {
151                 pnext->next = pcur;             //防止最后一个节点没有链接上倒数第二个
152             }
153             return;
154         }
155         pcur = pnext;  
156         pnext = pnext->next;  //上一步已经完成占位操作,之后让自己下移,记载下一个节点指针
157         pcur->next = ppre;  //经过上面两步,当前节点已经下移了一位,让自己的下一个指向之前的一个节点
158         ppre = pcur;    //上一步已经完成反向链接过程,让ppre后移一个节点
159     }
160 
161 }
162 
163 
164 LinkNode * LinkList::reserveByRecursion(LinkNode* hd)
165 {
166     if (NULL == hd->next)  //递归先找到最后一个节点
167     {
168         this->head->next = hd;
169         return hd;
170     }
171     LinkNode* pcurNode = reserveByRecursion(hd->next);  //是反转前的最后一个节点,反转后的第一个节点
172 
173     pcurNode->next = hd;  //此时hd代表反转前的前一个节点,进行逆向链接
174 
175     return hd;
176 }
177 
178 
179 void LinkList::ForEachLinkList()
180 {
181     LinkNode* pcurNode = this->head;
182 
183     for (int i = 0; i < this->length; ++i)
184     {
185         pcurNode = pcurNode->next;
186         cout << pcurNode->data << "   ";
187     }
188     cout << endl;
189 }
190 
191 LinkNode* LinkList::FindVal(int val)
192 {
193     if (this->length <= 0)
194     {
195         return NULL;
196     }
197 
198     LinkNode* pcurNode = head;
199     for (int i = 0; i < this->length; ++i)
200     {
201         pcurNode = pcurNode->next;
202         if (pcurNode->data == val)
203         {
204             cout << "找到了!" << endl;
205             return pcurNode;
206         }
207     }
208     return NULL;
209 }
210 
211 int LinkList::LinkListLength()
212 {
213     return this->length;
214 }
215 
216 
217 
218 void LinkList::clearList()
219 {
220     if (this->length <= 0)
221     {
222         return;
223     }
224     
225     LinkNode* pcurNode = head;
226     LinkNode* pnextNode = head->next;
227 
228     for (int i = 0; i < length; ++i)
229     {
230         pcurNode = pnextNode;
231         pnextNode = pcurNode->next;
232         if (pcurNode != NULL)
233         {
234             delete pcurNode;
235             pcurNode = NULL;
236         }
237     }
238 
239     this->length = NULL;
240 }
241 
242 LinkList::~LinkList()
243 {
244     if (this->length <= 0)
245     {
246         if (NULL != head)
247         {
248             delete head;
249             head = NULL;
250         }
251         return;
252     }
253 
254     LinkNode* pcurNode = head;
255     LinkNode* pnextNode = head->next;
256 
257     for (int i = 0; i < length; ++i)
258     {
259         pcurNode = pnextNode;
260         pnextNode = pcurNode->next;
261         if (pcurNode != NULL)
262         {
263             delete pcurNode;
264             pcurNode = NULL;
265         }
266     }
267     this->length = 0;
268     if (NULL != head)
269     {
270         delete head;
271         head = NULL;
272     }
273     return;
274 }
View Code

 

转载于:https://www.cnblogs.com/DLL137578736/p/7624234.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值