medium
给定一个数组,将数组中的元素向右移动 k
个位置,其中 k
是非负数。
进阶:
尽可能想出更多的解决方案,至少有三种不同的方法可以解决这个问题。
你可以使用空间复杂度为 O(1) 的 原地 算法解决这个问题吗?
示例 1:
输入: nums = [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
输入:nums = [-1,-100,3,99], k = 2
输出:[3,99,-1,-100]
解释:
向右旋转 1 步: [99,-1,-100,3]
向右旋转 2 步: [3,99,-1,-100]
第一种方法:
这一种方法也是我第一次就能想到的,就是通过另一个数组进行拷贝.不过我当时的写法比较困难,用了三个for()最后结果也是不对.我最开始的思路是,先把k之前的数先保存到一个新的数组,之后将k之后的数,移到原数组k之前的位置,之后再将新书组的数复制到原数组k之后的位置.
不过我最后也是没写出来,下面来看官方的思路,也是数组拷贝.
class Solution {
public void rotate(int[] nums, int k) {
int n = nums.length;
//创建一个新书组
int[] newArr = new int[n];
//原数组赋值到新数组的位置
for (int i = 0; i < n; i++) {
//这是最巧妙的一个地方,(i + k)%n起到了循环赋值的作用,就是说
//当i=0的时候原数组第一个元素放到了新书组k的位置,当i+K > n的时候就开始从头赋值
newArr[(i + k) % n] = nums[i];
}
//数组拷贝的方法System.arraycopy()
//newArr新数组引用,0开始的位置 nums原数组,0开始的位置,n原数组长度
//意思就是整体全部赋值过来
System.arraycopy(newArr, 0, nums, 0, n);
}
}
第二种方法
第二个方法就是暴力破解,可是当你提交的时候会出现超时
现在来看看代码
class Solution{
public void rotate(int[] nums,int k){
//防止k超出范围
k = k % nums.length;
int temp,pre;
//当i = 0时,此时下面的循环的最后一个元素放在第一位
//当i = 1是,最后一个元素放到第二位,新的元素放到第一位,以此类推
for(int i = 0;i < k;i++){
//最后一个值进行赋值
pre = nums[nums.length - 1];
//每次循环都将第i个元素与最后一个元素进行替换
for(int j = 0;j < nums.length;j++){
temp = nums[j];
nums[j] = pre;
pre = temp;
}
}
}
}
第三个实在没看懂,溜了....