Skip to content

Commit ad00d29

Browse files
committed
24.两两交换链表中的节点,递归,迭代
1 parent 5197117 commit ad00d29

File tree

3 files changed

+96
-0
lines changed

3 files changed

+96
-0
lines changed

leetcode_Java/DoneTitle.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
21. 合并两个有序链表
1515
22. 括号生成
1616
23. 合并K个升序链表
17+
24. 两两交换链表中的节点
1718
25. K 个一组翻转链表
1819
31. 下一个排列
1920
32. 最长有效括号

leetcode_Java/DoneType.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -111,6 +111,7 @@
111111
19. 删除链表的倒数第 N 个结点(递归,快慢指针,栈,计数)
112112
21. 合并两个有序链表(递归,迭代)
113113
23. 合并K个升序链表(顺序合并,分治合并)
114+
24. 两两交换链表中的节点(递归,迭代)
114115
25. K 个一组翻转链表(多指针)
115116
82. 删除排序链表中的重复元素 II(递归,双指针)
116117
83. 删除排序链表中的重复元素

leetcode_Java/Solution0024.java

Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
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

Comments
 (0)