题目
给定一个单向链表的头节点head,以及两个整数from和to,在单向链表上把第from个节点到第to个节点这一部分进行反转。
输入 | 调整结果为 |
1->2->3->4->5->null, from=2,to=4 | 1->4->3->2->5->null |
1->2->3->null, from=1,to=3 | 3->2->1->null |
要求
- 如果链表长度为N,时间复杂度为O(N),额外空间复杂度要求为O(1)
- 如果不满足1<=from<=to<=N,则不用调整
思路
- 先判断如果不满足要求2,则直接返回头节点
- 找到from-1的节点fPre和to+1的节点tPos,现把中间需要反转的部分反转,再正确地连接tPre和tPos。
- 如果tPre为空,说明头节点在反转部分内,则需要返回新的头节点。如果不为空则返回之前的头节点。
源码
public class Node{
public int value;
public Node next;
public Node(int data){
this.value=data;
}
}
public Node reversePart(Node head,int from,int to){
int len=0;
//新的头节点
Node node1=head;
Node fPre=null;
Node tPos=null;
//找到tPre和tPos
while(node1!=null){
len++;
fPre=len==from-1?node1:fPre;
tPos=len==to+1?node1:tPos;
node1=node.next;
}
//第一阶段
if(from>to||from<1||to>len){
return head;
}
//第二阶段,进行反转
node1=fPre==null?head:fPre.next;
Node node2=node1.next;
node1.next=tPos;
Node next=null;
while(node2!=tPos){
next=node2.next;
node2.next=node1;
node1=node2;
node2=next;
}
//第三部判断fPre是否为空
if(fPre!=null){
fPre.next=node1;
return head;
}
return node1;
}