您好,登录后才能下订单哦!
密码登录
登录注册
点击 登录注册 即表示同意《亿速云用户服务条款》
# 怎么使用Java实现单链表的反转
## 目录
1. [单链表基础概念](#单链表基础概念)
2. [反转链表的算法思路](#反转链表的算法思路)
3. [迭代法实现](#迭代法实现)
4. [递归法实现](#递归法实现)
5. [栈辅助实现](#栈辅助实现)
6. [复杂度分析与对比](#复杂度分析与对比)
7. [完整代码示例](#完整代码示例)
8. [应用场景与扩展](#应用场景与扩展)
---
## 单链表基础概念
单链表(Singly Linked List)是由节点组成的线性数据结构,每个节点包含:
- **数据域**:存储实际数据
- **指针域**:指向下一个节点的地址
```java
class ListNode {
int val;
ListNode next;
ListNode(int x) { val = x; }
}
特点: - 非连续内存存储 - 插入/删除时间复杂度O(1) - 随机访问时间复杂度O(n)
核心目标:将A->B->C->D
变为D->C->B->A
最常用且空间复杂度最优的方法(O(1))
public ListNode reverseList(ListNode head) {
ListNode prev = null;
ListNode curr = head;
while (curr != null) {
ListNode nextTemp = curr.next; // 1.保存next节点
curr.next = prev; // 2.反转指针
prev = curr; // 3.移动prev
curr = nextTemp; // 4.移动curr
}
return prev;
}
初始状态:1 -> 2 -> 3 -> null
第1次迭代:
prev = null
curr = 1
nextTemp = 2
1.next -> null
prev = 1
curr = 2
第2次迭代:
nextTemp = 3
2.next -> 1
prev = 2
curr = 3
第3次迭代:
nextTemp = null
3.next -> 2
prev = 3
curr = null
更简洁但空间复杂度为O(n)(递归栈深度)
public ListNode reverseList(ListNode head) {
if (head == null || head.next == null) {
return head;
}
ListNode newHead = reverseList(head.next);
head.next.next = head; // 反转指针
head.next = null; // 断开原指针
return newHead;
}
reverseList(1):
reverseList(2):
reverseList(3): return 3
2.next.next = 2 → 3->2
2.next = null
return 3
1.next.next = 1 → 2->1
1.next = null
return 3
利用栈后进先出的特性实现反转
public ListNode reverseList(ListNode head) {
if (head == null) return null;
Stack<ListNode> stack = new Stack<>();
while (head != null) {
stack.push(head);
head = head.next;
}
ListNode newHead = stack.pop();
ListNode curr = newHead;
while (!stack.isEmpty()) {
curr.next = stack.pop();
curr = curr.next;
}
curr.next = null; // 防止循环引用
return newHead;
}
方法 | 时间复杂度 | 空间复杂度 | 适用场景 |
---|---|---|---|
迭代法 | O(n) | O(1) | 内存敏感场景 |
递归法 | O(n) | O(n) | 代码简洁性优先 |
栈辅助 | O(n) | O(n) | 需要保存节点时 |
包含测试用例的完整实现:
public class LinkedListReverser {
// 节点定义
static class ListNode {
int val;
ListNode next;
ListNode(int val) { this.val = val; }
}
// 迭代法
public static ListNode reverseIteratively(ListNode head) {
/* 同前文实现 */
}
// 递归法
public static ListNode reverseRecursively(ListNode head) {
/* 同前文实现 */
}
// 打印链表
public static void printList(ListNode head) {
while (head != null) {
System.out.print(head.val + " ");
head = head.next;
}
System.out.println();
}
public static void main(String[] args) {
// 构建测试链表 1->2->3->4
ListNode head = new ListNode(1);
head.next = new ListNode(2);
head.next.next = new ListNode(3);
head.next.next.next = new ListNode(4);
System.out.println("原始链表:");
printList(head);
System.out.println("迭代反转后:");
printList(reverseIteratively(head));
System.out.println("递归反转后:");
printList(reverseRecursively(head));
}
}
ListNode successor = null;
ListNode reverseN(ListNode head, int n) {
if (n == 1) {
successor = head.next;
return head;
}
ListNode newHead = reverseN(head.next, n-1);
head.next.next = head;
head.next = successor;
return newHead;
}
ListNode reverseBetween(ListNode head, int m, int n) {
if (m == 1) {
return reverseN(head, n);
}
head.next = reverseBetween(head.next, m-1, n-1);
return head;
}
ListNode reverseKGroup(ListNode head, int k) {
ListNode curr = head;
int count = 0;
while (curr != null && count < k) {
curr = curr.next;
count++;
}
if (count == k) {
curr = reverseKGroup(curr, k);
while (count-- > 0) {
ListNode temp = head.next;
head.next = curr;
curr = head;
head = temp;
}
head = curr;
}
return head;
}
注意:在实际面试中,面试官可能会要求同时写出迭代和递归两种解法,并分析它们的优缺点。建议掌握至少两种实现方式。 “`
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。