系列文章目录
1 反转链表
题目
输入:1->2->3->4->5
输出:5->4->3->2->1
一、解题思路
1.解法一(迭代)
- 从前往后遍历链表,将当前节点的next指向上一个节点,因此需要一个变量prev存储上一个节点;
- 当前节点处理完需要寻找下一个节点,因此需要一个变量curr保存当前节点;
- 处理完后要将当前节点赋值给prev,并将下一个节点赋值给curr,因此需要一个变量提前保存下一个节点。
因此共需要三个变量prev、curr、next。
2.解法二(递归)
以类似的方法重复,先找到链表的最后一个节点,从最后一个节点开始遍历,将大的问题(链表反转)拆解成相同性质的小问题(两个元素反转),将所有的小问题解决,大问题也就解决。
二、代码
1.定义链表节点
代码如下(示例):
// 链表节点
static class ListNode {
int val;
ListNode next;
public ListNode(int val, ListNode next){
this.val =val;
this.next = next;
}
}
2.迭代
代码如下(示例):
public static ListNode iterate(ListNode head){
// prev在最前面,curr在中间,next在后面
ListNode prev = null,next;
ListNode curr = head;
while (curr != null){
next = curr.next; //先保存下一个节点
curr.next = prev; //curr的指针往前指,同时断开原来的连接,转置
prev = curr; //prev指针后移一个
curr = next; //curr指针后移一个
}
return prev; //返回头节点
}
2.递归
代码如下(示例):
public static ListNode recursion(ListNode head){
if (head == null || head.next == null){
// 若节点为空,那么返回 null;若节点是最后一个节点,那么返回最后一个节点(转置后的头节点)
return head;
}
// 自己调自己,找到最后一个节点,返回最后一个节点,即转置后的头节点
ListNode new_head = recursion(head.next);
head.next.next = head;
head.next = null;
return new_head; //返回头节点
}
2.调用
代码如下(示例):
public static void main(String[] args) {
ListNode node5 = new ListNode(5, null);
ListNode node4 = new ListNode(4, node5);
ListNode node3 = new ListNode(3, node4);
ListNode node2 = new ListNode(2, node3);
ListNode node1 = new ListNode(1, node2); //1,2,3,4,5
//1.迭代求转置
//ListNode node = iterate(node1);
//2.递归求转置
ListNode node = iterate(node1);
while (node != null){
System.out.println(node.val);
node = node.next;
}
}