1
+ // 24. 两两交换链表中的节点
2
+
3
+
4
+ /**
5
+ * Definition for singly-linked list.
6
+ * public class ListNode {
7
+ * int val;
8
+ * ListNode next;
9
+ * ListNode() {}
10
+ * ListNode(int val) { this.val = val; }
11
+ * ListNode(int val, ListNode next) { this.val = val; this.next = next; }
12
+ * }
13
+ */
14
+
15
+
16
+ /*
17
+ 递归:
18
+ 1、方法功能:入参是一个节点,修改当前节点和下一节点指针方向,交换两个节点,返回新的头节点
19
+ 2、终止条件:head或head.next为空则直接返回头节点,因为交换至少需要两个节点
20
+ 3、返回结果:交换完成后新的头节点
21
+ 4、递归逻辑:
22
+ 1)两个节点交换完成后,新的尾节点连接着后续链表的头节点,而后续链表的头节点需要同样的交换操作,因此调用同样的方法递归处理
23
+ 2)0个、1个节点的情况在终止条件中包含,单层递归时可以把链表当成只有2个或3个节点的简单情况,前两个节点交换完成后,连接着第三个节点newHead.next,
24
+ newHead.next作为新的头节点,同样需要交换,因此调用同样的方法
25
+
26
+ 1 2 3 4
27
+ ↑ ↑
28
+ head newHead
29
+ */
30
+ class Solution {
31
+ public ListNode swapPairs (ListNode head ) {
32
+ if (head == null || head .next == null ) {
33
+ return head ;
34
+ }
35
+ ListNode newHead = head .next ;
36
+ head .next = swapPairs (newHead .next );
37
+ newHead .next = head ;
38
+ return newHead ;
39
+ }
40
+ }
41
+
42
+
43
+ /*
44
+ 递归:
45
+ 思路同上。上一解法第三个节点用newHead.next获取,所以要先连接好第三个节点后,newHead.next指针才能移动。
46
+ 本解法第三个节点直接用一个新的指针temp标记,所以可以先移动newHead.next指针,不会丢失第三个节点的引用。
47
+
48
+ 1 2 3 4
49
+ ↑ ↑ ↑
50
+ head newHead temp
51
+ */
52
+ class Solution {
53
+ public ListNode swapPairs (ListNode head ) {
54
+ if (head == null || head .next == null ) {
55
+ return head ;
56
+ }
57
+ ListNode temp = head .next .next ;
58
+ ListNode newHead = head .next ;
59
+ newHead .next = head ;
60
+ head .next = swapPairs (temp );
61
+ return newHead ;
62
+ }
63
+ }
64
+
65
+
66
+ /*
67
+ 迭代:
68
+ 1、多指针标记用到的节点
69
+ 2、修改节点指针方向
70
+ 3、重新初始化指针,标记下一次交换的节点
71
+
72
+ 0 1 2 3 4
73
+ ↑ ↑ ↑
74
+ root/pre start end
75
+ ============================
76
+ 0 2 1 3 4
77
+ ↑ ↑ ↑ ↑
78
+ root pre start end
79
+ */
80
+ class Solution {
81
+ public ListNode swapPairs (ListNode head ) {
82
+ ListNode root = new ListNode (0 , head );
83
+ ListNode pre = root ;
84
+ while (pre .next != null && pre .next .next != null ) {
85
+ ListNode start = pre .next ;
86
+ ListNode end = pre .next .next ;
87
+ pre .next = end ;
88
+ start .next = end .next ;
89
+ end .next = start ;
90
+ pre = start ;
91
+ }
92
+ return root .next ;
93
+ }
94
+ }
0 commit comments