题目
给你一个链表的头节点 head ,旋转链表,将链表每个节点向右移动 k 个位置。
输入:head = [1,2,3,4,5], k = 2
输出:[4,5,1,2,3]
方法一
先判断输入是否为NULL或者k0,不为空的话,找到链表的长度,然后向右移动k % length== 步。
初步想的是用数组来实现。这样空间复杂度为O(n),时间复杂度为O(n).
class Solution {
public:
ListNode* rotateRight(ListNode* head, int k) {
int length = 0;
if (k == 0 || head == nullptr || head->next == nullptr) {
return head;
}
//得到数组长度,length代表长度 (temp->next != nullptr)则length代表最后一个元素的索引
ListNode* temp = head;
while(temp != nullptr){
length++;
temp = temp->next;
}
int before[length],after[length];
//把链表变成数组
temp = head;
for(int i = 0;i < length;i++){
before[i] = temp->val;
temp = temp->next;
}
//找索引的规律
for(int i = 0;i < length;i++){
after[(i+k)%length] = before[i];
}
//把数组变成链表
temp = head;
for(int i = 0;i < length;i++){
temp->val = after[i];
temp = temp->next;
}
return head;
}
};
方法二:直接对链表操作
官方题解就是这么做的,分析见注释。
class Solution {
public:
ListNode* rotateRight(ListNode* head, int k) {
//判断是否为NULL
if (k == 0 || head == nullptr || head->next == nullptr) {
return head;
}
//得到链表长度
int n = 1;
ListNode* iter = head;
while (iter->next != nullptr) {
iter = iter->next;
n++;
}
//如果k是n的倍数,那么就不移动,而不是让他移动n圈再返回结果。
int add = n - k % n;
if (add == n) {
return head;
}
//
iter->next = head;
while (add--) {
iter = iter->next;
}
ListNode* ret = iter->next;
iter->next = nullptr;
return ret;
}
};
链表节点初始化
head=(ListNode*)malloc(sizeof(ListNode));
head->next=NULL;