Given an array, move the elements in the array to the right k k k locations, where k k k is a nonnegative number.
Advanced:
Think of as many solutions as possible. There are at least three different ways to solve this problem.
You can use space complexity as O ( 1 ) O(1) Of O(1) In situ Does the algorithm solve this problem?
Example 1:
Input: nums = [1,2,3,4,5,6,7], k = 3Output: [5,6,7,1,2,3,4]
Explanation:
Rotate one step to the right: [7,1,2,3,4,5,6]
Rotate 2 steps to the right: [6,7,1,2,3,4,5]
Rotate 3 steps to the right: [5,6,7,1,2,3,4] Example 2: Input: num = [- 1, - 100,3,99], k = 2
Output: [3,99, - 1, - 100]
Explanation:
Rotate 1 step to the right: [99, - 1, - 100,3]
Rotate 2 steps to the right: [3,99, - 1, - 100]
Tips:
1 < = n u m s . l e n g t h < = 2 ∗ 104 1 <= nums.length <= 2 * 104 1<=nums.length<=2∗104
− 231 < = n u m s [ i ] < = 231 − 1 -231 <= nums[i] <= 231 - 1 −231<=nums[i]<=231−1
0 < = k < = 105 0 <= k <= 105 0<=k<=105
1. Use temporary array
You can use a temporary array. First store the value of the original array in a temporary array, and then reassign the value of the temporary array to the original array. When reassigning, ensure that each element moves back k k k-bit. If it exceeds the length of the array, it starts from scratch, so it can be used here ( i + k ) (i + k) (i+k) % l e n g t h length length to calculate the index of the reassigned element.
code:
public void rotate(int nums[], int k) { int length = nums.length; int temp[] = new int[length]; //Put the original array value into a temporary array, for (int i = 0; i < length; i++) { temp[i] = nums[i]; } //Then put the value of the temporary array back into the original array and move k bits to the right for (int i = 0; i < length; i++) { nums[(i + k) % length] = temp[i]; } }
2. Multiple inversion
First invert all arrays, k before inverting, and finally invert the rest.
code:
public void rotate(int[] nums, int k) { int length = nums.length; k %= length; reverse(nums, 0, length - 1);//Invert all elements first reverse(nums, 0, k - 1);//Invert the first k elements reverse(nums, k, length - 1);//Then reverse the rest } //Exchange the elements in the array from [start, end] in pairs, that is, reverse public void reverse(int[] nums, int start, int end) { while (start < end) { int temp = nums[start]; nums[start++] = nums[end]; nums[end--] = temp; } }
In fact, under adjustment, you can first reverse the front, then reverse the k behind, and finally reverse all. The principle is the same
code:
public void rotate(int[] nums, int k) { int length = nums.length; k %= length; reverse(nums, 0, length - k - 1);//Reverse the previous one first reverse(nums, length - k, length - 1);//Then reverse the last k reverse(nums, 0, length - 1);//Finally, all elements are reversed } //Exchange the elements in the array from [start, end] in pairs, that is, reverse public void reverse(int[] nums, int start, int end) { while (start < end) { int temp = nums[start]; nums[start++] = nums[end]; nums[end--] = temp; } }
3. Circular rotation
Like Joseph's ring, it is easy to understand that the array is regarded as a ring, and each moves back k bits
be careful:
But there's a pit here, if ( i + k ) (i + k) (i+k) % l e n g t h = 0 length=0 length=0, that is, the array length is k k Multiple of k, this will rotate in place, as shown in the figure below
For this problem, we can use an array v i s i t e d visited visited indicates whether this element has been accessed. If it has been accessed, start from the next one to prevent it from rotating in place.
code:
public static void rotate(int[] nums, int k) { int hold = nums[0]; int index = 0; int length = nums.length; boolean[] visited = new boolean[length]; for (int i = 0; i < length; i++) { index = (index + k) % length; if (visited[index]) { //If you have visited and visited again, you will turn around in place, //We can no longer access the current element. Let's start with its next element index = (index + 1) % length; hold = nums[index]; i--; } else { //Save the current value in the next location. Before saving, save the current value in the next location //Record the value visited[index] = true; int temp = nums[index]; nums[index] = hold; hold = temp; } } }
Reference article: https://leetcode-cn.com/leetbook/read/top-interview-questions-easy/x2skh7/