给定一个链表,旋转链表,使得每个节点向右移动k个位置,其中k是一个非负数
样例
给出链表1->2->3->4->5->null和k=2
返回4->5->1->2->3->null
解题思路:
双指针法。
需要注意旋转操作,需要取k除链表长度的余数。
/**
* Definition for ListNode
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
/**
* @param head: the List
* @param k: rotate to the right k places
* @return: the list after rotation
*/
public ListNode rotateRight(ListNode head, int k) {
// write your code here
int length = getLength(head);
if(length == 0)
return null;
k = k%length;
if(k == 0)
return head;
ListNode thisK = head;//指向旋转后的新头
ListNode preK = head;//指向k前一个元素
ListNode end = head;//指向链表最后一个元素
for(int i=1 ; i<length ; i++){
if(i<=(length-k)){
preK = thisK;
thisK = thisK.next;
}
end = end.next;
}
end.next = head;
preK.next = null;
return thisK;
}
public int getLength(ListNode head){
int res = 0;
while(head != null){
head = head.next;
res++;
}
return res;
}
}
二刷:
/**
* Definition for ListNode
* public class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
public class Solution {
/**
* @param head: the List
* @param k: rotate to the right k places
* @return: the list after rotation
*/
public ListNode rotateRight(ListNode head, int k) {
// write your code here
if(head == null)
return head;
int len = getLens(head);
k = k%len;
if(len <= 1 || k == 0)
return head;
ListNode dummy = new ListNode(0);
ListNode lPre = null;//指向lNode的前一个元素
//head[lNode...rNode]前闭后闭区间为需要旋转的区间
ListNode lNode = head;
ListNode rNode = head;
for(int i=1; i<k; i++)
rNode = rNode.next;
while(rNode.next != null){
lPre = lNode;
rNode = rNode.next;
lNode = lNode.next;
}
dummy.next = lNode;
rNode.next = head;
lPre.next = null;
return dummy.next;
}
private int getLens(ListNode head){
int res = 0;
while(head != null){
head = head.next;
res++;
}
return res;
}
}