Reverse a linked list from position m to n. Do it in-place and in one-pass.
For example:
Given1->2->3->4->5->NULL, m = 2 and n = 4,
return1->4->3->2->5->NULL.
Note:
Given m, n satisfy the following condition:
1 ≤ m ≤ n ≤ length of list.
题目中有两点需要注意的是:一、m和n数字和结点的对应关系;二、1 ≤ m ≤ n ≤ length of list,意味着,第一,可以从表头开始反转,第二,不用考虑n>length of list的情况。
思路:因为可以从表头开始反转,所以要new一个nList。首先要找到反转的起始结点cur和其前驱pre,然后将前驱pre的后继为cur的next,而cur的后继则为后继的后继,cur后继的后继为pre的后继。有点拗口!脑海中可以想象为,整个过程,pre不动,cur本身指向的结点不动,但给人的感觉是不断后移的。以1->2->3->4->5->NULL, m = 2 and n = 4,为例。
另外值得注意的是,代码中,两个for循环的使用。代码如下:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode(int x) : val(x), next(NULL) {}
* };
*/
class Solution {
public:
ListNode *reverseBetween(ListNode *head, int m, int n)
{
if(head==NULL) return NULL; ListNode *nList=new ListNode();
nList->next=head; ListNode *cur=head;
ListNode *pre=nList;
for(int i=;i<m;++i)
{
pre=cur;
cur=cur->next;
}
for(int i=;i<n-m;++i)
{
ListNode *temp=cur->next;
cur->next=temp->next;
temp->next=pre->next;
pre->next=temp;
}
return nList->next;
}
};
//或者也可以,分成三部分,m之前,[m,n],n之后,然后将[m,n]进行反转,然后连接三段。