翻转链表 II
题目
翻转链表中第m个节点到第n个节点的部分
注意事项
m,n满足1 ≤ m ≤ n ≤ 链表长度样例
给出链表1->2->3->4->5->null, m = 2 和n = 4,返回1->4->3->2->5->null
挑战
在原地一次翻转完成
题解
1.Stack法
对于要翻转部分的节点,用Stack辅助进行翻转,然后再与首尾部分进行拼接。
/**
* Definition for ListNode
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
/**
* @param ListNode head is the head of the linked list
* @oaram m and n
* @return: The head of the reversed ListNode
*/
public ListNode reverseBetween(ListNode head, int m , int n) {
if (m == n)
{
return head;
}
int count = 1;
ListNode newHead = new ListNode(1);
newHead.next = head;
ListNode mPre = newHead;
ListNode nTail = null;
Stack<ListNode> stack = new Stack<>();
while (head != null)
{
if (count < m)
{
mPre = mPre.next;
}
else if (count >= m && count <= n)
{
stack.push(head);
if (count == n)
{
nTail = head.next;
break;
}
}
head = head.next;
count++;
}
while (!stack.isEmpty())
{
mPre.next = stack.pop();
mPre = mPre.next;
}
mPre.next = nTail;
return newHead.next;
}
}
2.原地翻转
为了方便处理,先给链表加上一个头结点dummy,dummy->1->2->3->4->5->null。然后将head指向dummy节点,开始遍历链表,将head移动到第一个需要翻转的节点的前节点,即head指向1。
先保存3的后继节点,再将节点3指向其前节点2,变成dummy->1->2<-3 4->5->null,再将节点后移一位,继续处理节点3和节点4,。最后将节点首尾相连即可。
/**
* Definition for ListNode
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
/**
* @param ListNode head is the head of the linked list
* @oaram m and n
* @return: The head of the reversed ListNode
*/
public ListNode reverseBetween(ListNode head, int m , int n) {
ListNode dummy = new ListNode(0);
dummy.next = head;
head = dummy;
for (int i = 1; i < m; i++)
{
head = head.next;
}
ListNode mNode = head.next;
ListNode nNode = mNode;
ListNode postnNode = mNode.next;
for (int i = m; i < n; i++)
{
ListNode temp = postnNode.next;
postnNode.next = mNode;
mNode = postnNode;
postnNode = temp;
}
nNode.next = postnNode;
head.next = mNode;
return dummy.next;
}
}
Last Update 2016.9.26