之前遇到反转链表的算法,比较晦涩难解,但其实挺简单的。
目标:将一个顺序链表反转。
思路:用三个辅助节点,每次实现一个节点的指向反转,即他的后继变为他的前驱。
三个辅助节点: p q r 按顺序分别指向 节点0,1,2, 然后一次次移动,指向1,2,3 ; 2,3,4......
算法分为三部分:
第一部分:初始化部分:
q是中心节点,是每次反转的节点,于是q是由函数参数传入的,前面的节点p一个是null,后面的节点r是q的后继节点q.next
第二部分:循环部分
分为两个操作:
1.反转:q的后继变为他的前驱: q.next = p
2.移动:pqr向后移动一位: p = q; q = r; r = r.next;
第三部分:尾部处理:
反转最后一个节点,并返回
1 public Node inverse(Node q) {//q初始化为头结点:一开始是: p=null,q=head r = head.next 2 //参考:https://blog.csdn.net/feliciafay/article/details/6841115 3 if (q == null) return null;//头结点为null,退出 4 /** 5 * 初始化部分:p=null,q=head(由函数参数传入) r = q.next 6 */ 7 // 一开始是: p=null,q=head r = head.next 8 Node r = q.next; //r是记录还有多少个节点,即p q r,如果r=null,表示后面已经没有更多的节点了,初始化为第二个 9 Node p = null; //初始化为null 10 /** 11 * 循环部分: q反转 + pqr整体移动。 12 */ 13 while (r != null) { //当当前节点有后继节点时 14 //反转节点q. (注意:q 是中心节点) 15 q.next = p;//q的后继节点指向他的父节点p 16 //p,q,r相继往后移动 17 p = q; //p后移动一个节点,即指向后继q 18 q = r; //q也往后移动一个节点,指向后继r 19 r = r.next;//r移动到下一个节点 20 } 21 /** 22 * 尾部处理部分:q反转 23 */ 24 q.next = p;//由于r到了最后节点的空子节点后,p,q还未反转,故将其反转 25 return q;//返回新的头结点,即原来的尾节点 26 }
1 //节点类 2 static class Node {// 3 Node next; 4 int data; 5 6 Node(int data) { 7 this.data = data; 8 } 9 }
2018-12-11 13:24:26 DuXia Library XT
原文地址:https://www.cnblogs.com/XT-xutao/p/10101623.html
时间: 2024-11-05 20:34:06