数据结构(2):单向链表的反转
来源:互联网 发布:怎样开淘宝网店代销 编辑:程序博客网 时间:2024/06/15 03:32
单向链表的反转。记住3点:1. 反转;2. 封口;3. 找到新的head。
画图解决问题。1. 画list;2. 画stack(递归的时候)。
不用递归,从前往后反转比较好写。
用递归,从后往前反转。
非递归的做法
1. 没有节点,返回nullptr;
2. 只有1个结点,不用反转,返回头指针;
3. 有大于或等于2个结点,这是要保存连续的3个结点。不然,断开以后,找不到下一个元素在哪里。
如果到尾了(下一个结点是nullptr),就把这个尾巴保存为新的头,最后返回。
转向的时候:
(0) 原始list的头的next先置为nullptr;
(1) 一定要先保存下一个结点,e.g. 用s保存;
(2) 把当前结点p的next指向上一个结点q;
然后再把p、q、s都往前挪一位。(s其实是在while一开始就往后挪了)
用3个指针做!
/************************************************************************//* 单向链表(2):反转qcy2017年1月4日19:35:45*//************************************************************************/#include <iostream>using namespace std;typedef struct LNode{int data;LNode * next;} LNode, *Linklist;void printList(Linklist list) {while (list){cout<<list->data<<" ";list = list->next;}cout<<"\n";}// 反转listLinklist reverseList(Linklist list) {if (!list) // 0个元素return nullptr;else if(!(list->next)) // 1个元素return list; // 不作任何改变// 大于等于2个元素 --> 要保留 连续的三个元素!!! [记住,记住…]else {LNode *p,*q, *s;LNode *newHead;q = list;p = list->next;list->next = nullptr; // 把第一个元素的next至0// 那p有没有为nullptr?? 没有啊!while (p) // 当前节点没有到头{s = p->next; // 1. 把即将反转的结点的下一个先保存下来。不然一会儿找不到。//////////if (!s) // 如果当前的next走到list的末尾了,新链表头就是当前的结点newHead = p; // 2. p的next指向q(转向)p->next = q;// 3. p和q分别往前走q = p;p = s;}return newHead;}}int main () {const int N = 10;int iArray[N] = {1,2,3,4,5,6,7,8,9,10};Linklist list,head,p;list = new LNode;head = list;p = head;// 第1个list->data = iArray[0];list->next = nullptr;// 之后的for (int i = 1;i<N;i++){LNode * node = new LNode;node->data = iArray[i];node->next = nullptr;p->next = node;p = p->next;}printList(head);//////////////////////////////////////////////////////////////////////////// 把list反个顺序 // 多画几个图!!head = reverseList(list); list = head; cout<<"反转list"<<endl; printList(list);system("pause");return 0;}1 2 3 4 5 6 7 8 9 10
反转list
10 9 8 7 6 5 4 3 2 1
递归做法
Linklist myRerverseRecursion(Linklist head) {// 如果当前节点到了list的末尾了,就返回当前节点if (head == nullptr || head->next == nullptr){return head;} else {// 1. 继续前进,直到找到list的尾部,作为新的headLinklist newHead = myRerverseRecursion(head->next);// 2. 出了栈(上面的函数结束以后)以后,就反转、封口// (head->next)->next = head; // 简单写法。反转LNode * nextNode = head->next; // 分步写反转nextNode->next = head; // 反转head->next = nullptr; // 封口return newHead; // 不断地返回,使得上面一定能得到list的尾巴(新的头结点)}}建议:画出stack!画出list!
反转、封口。
0 0
- 数据结构(2):单向链表的反转
- 数据结构之链表面试题汇总(二)-有序单向链表的合并、单向链表反转
- 单向链表的反转
- 单向链表的反转
- 单向链表的反转
- 单向链表的反转
- 单向链表的反转
- 单向链表的反转
- 单向链表的反转
- 单向链表反转
- 反转单向链表
- 单向链表反转
- 单向链表反转
- 单向链表反转
- 反转单向链表
- 反转单向链表
- 反转单向链表
- 反转单向链表
- 第一周 + 周末项目文档
- 最大值[JSOI2008] 洛谷1198 线段树
- 【BZOJ 2438】[中山市选2011]杀人游戏 概率+联通分量
- Decode Ways
- 计算机--机器学习---机器learning基石sum
- 数据结构(2):单向链表的反转
- Hadoop 图像小文件查重方法
- IntelliJ IDEA 最常用快捷键
- 使用模板生成xml格式
- 积少成多,记录java菜鸟的成长之路(一)
- 第二周+周五笔记
- 将连个图片合并成一个
- Intent 和 Intent 过滤器
- jQuery学习之jQuery Ajax用法详解