题目:https://leetcode-cn.com/problems/rotate-list/
我的方法一
技巧
在链表操作里,经常设置一个哨兵节点,是为了操作简单;
步骤
- 先遍历一遍链表,得到链表的长度;也保存链表的尾tail,后面会用;
- 移动的k步数除以链表长度得到的余数,就是有效的移动的最小步数
- 移动k-1步,获得新列表的最后一个节点new_tail,新链表头设为new_tail的next;new_tail的next设为null;tail的next设为原来的head;
- 返回新链表头;
边界条件
- 当head为空时表示链表为空不需要移动;
- 当链表长度是1时也不需要移动;
- 当移动的最小有效步数为0时,也不需要移动;
复杂度
时间复杂度:O(N),因为遍历一遍列表O(N),找到新的最后一个节点是O(N-k);所以总体时O(N)
空间复杂度:O(1),因为是原地移动
代码
class Solution {
public:
ListNode* rotateRight(ListNode* head, int k) {
if(!head){
return nullptr;
}
ListNode* tail = nullptr;
int list_len = 0;
ListNode* node = head;
while(node){
tail = node;
node = node->next;
list_len++;
}
int step = k % list_len;
if(step == 0){
return head;
}
step = list_len - step;
ListNode sentinal;
sentinal.next = head;
node = &sentinal;
while(step > 0){
node = node->next;
step--;
}
sentinal.next = node->next;
node->next = nullptr;
tail->next = head;
return sentinal.next;
}
};