给定一个数组,将数组中的元素向右移动 k 个位置,其中 k 是非负数。
示例 1:
输入:
[1,2,3,4,5,6,7]
和 k = 3
输出:
[5,6,7,1,2,3,4]
解释:
向右旋转 1 步:[7,1,2,3,4,5,6]
向右旋转 2 步: [6,7,1,2,3,4,5]
向右旋转 3 步:[5,6,7,1,2,3,4]
示例 2:
输入:[-1,-100,3,99]
和 k = 2
输出: [3,99,-1,-100]
解释:
向右旋转 1 步: [99,-1,-100,3]
向右旋转 2 步: [3,99,-1,-100]
说明:
- 尽可能想出更多的解决方案,至少有三种不同的方法可以解决这个问题。
- 要求使用空间复杂度为 O(1) 的原地算法。
方法一:每次向右移动一位,移动k次。380ms
class Solution {
public:
void rotate(vector<int>& nums, int k) {
for(int j=0;j<k;j++){
int tmp=nums[nums.size()-1];
for(int i=nums.size()-1;i>0;i--){
nums[i]=nums[i-1];
}
nums[0]=tmp;
}
}
};
改进方法:先是逆序数组中全部的元素,然后在分别逆序前k个和后size-k个元素 16 ms
class Solution {
public:
void rotate(vector<int>& nums, int k) {
int size=nums.size();
if(size<2)return;
if(k>=size)k=k%size;
reverse(nums.begin(),nums.end());
reverse(nums.begin(),nums.begin()+k);
reverse(nums.begin()+k,nums.end());
}
};
注:C++ < algorithm > 中定义的reverse函数用于反转在[first,last)范围内的顺序
template <class BidirectionalIterator>
void reverse (BidirectionalIterator first,BidirectionalIterator last);
// reverse algorithm example
#include <iostream> // std::cout
#include <algorithm> // std::reverse
#include <vector> // std::vector
int main () {
std::vector<int> myvector;
// set some values:
for (int i=1; i<10; ++i) myvector.push_back(i); // 1 2 3 4 5 6 7 8 9
std::reverse(myvector.begin(),myvector.end()); // 9 8 7 6 5 4 3 2 1
// print out content:
std::cout << "myvector contains:";
for (std::vector<int>::iterator it=myvector.begin(); it!=myvector.end(); ++it)
std::cout << ' ' << *it;
std::cout << '\n';
return 0;
}
函数行为等效于:
template <class BidirectionalIterator>
void reverse (BidirectionalIterator first, BidirectionalIterator last)
{
while ((first!=last)&&(first!=--last))
{
std::iter_swap (first,last);
++first;
}
}