Skip to content

Commit 8a15998

Browse files
committed
rotate array
1 parent 8646aa7 commit 8a15998

File tree

2 files changed

+206
-0
lines changed

2 files changed

+206
-0
lines changed

189.rotate_array/rotate.go

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
// 189. Rotate array
2+
// Topics: 'Array', 'Math', 'Two pointer'
3+
// Level: 'Medium'
4+
5+
//Given an integer array nums, rotate the array to the right by k steps, where k is non-negative.
6+
7+
// Example 1:
8+
9+
// Input: nums = [1,2,3,4,5,6,7], k = 3
10+
// Output: [5,6,7,1,2,3,4]
11+
// Explanation:
12+
// rotate 1 steps to the right: [7,1,2,3,4,5,6]
13+
// rotate 2 steps to the right: [6,7,1,2,3,4,5]
14+
// rotate 3 steps to the right: [5,6,7,1,2,3,4]
15+
16+
// Example 2:
17+
18+
// Input: nums = [-1,-100,3,99], k = 2
19+
// Output: [3,99,-1,-100]
20+
// Explanation:
21+
// rotate 1 steps to the right: [99,-1,-100,3]
22+
// rotate 2 steps to the right: [3,99,-1,-100]
23+
24+
// Constraints:
25+
26+
// 1 <= nums.length <= 105
27+
// -231 <= nums[i] <= 231 - 1
28+
// 0 <= k <= 105
29+
30+
// Follow up:
31+
32+
// Try to come up with as many solutions as you can. There are at least three different ways to solve this problem.
33+
// Could you do it in-place with O(1) extra space?
34+
35+
package rotatearray
36+
37+
func rotate(nums []int, k int) {
38+
k = k % len(nums)
39+
if k == 0 {
40+
return
41+
}
42+
k = k % len(nums)
43+
if k == 0 {
44+
return
45+
}
46+
reverse(nums)
47+
reverse(nums[:k])
48+
reverse(nums[k:])
49+
}
50+
51+
func reverse(nums []int) {
52+
for i, j := 0, len(nums)-1; i < j; {
53+
nums[i], nums[j] = nums[j], nums[i]
54+
i++
55+
j--
56+
}
57+
}

189.rotate_array/rotate_test.go

Lines changed: 149 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,149 @@
1+
package rotatearray
2+
3+
import (
4+
"reflect"
5+
"testing"
6+
)
7+
8+
func TestRotate(t *testing.T) {
9+
tests := []struct {
10+
name string
11+
nums []int
12+
k int
13+
want []int
14+
}{
15+
{
16+
name: "example 1 - rotate by 3",
17+
nums: []int{1, 2, 3, 4, 5, 6, 7},
18+
k: 3,
19+
want: []int{5, 6, 7, 1, 2, 3, 4},
20+
},
21+
{
22+
name: "example 2 - rotate by 2",
23+
nums: []int{-1, -100, 3, 99},
24+
k: 2,
25+
want: []int{3, 99, -1, -100},
26+
},
27+
{
28+
name: "k equals array length",
29+
nums: []int{1, 2, 3, 4},
30+
k: 4,
31+
want: []int{1, 2, 3, 4},
32+
},
33+
{
34+
name: "k greater than array length",
35+
nums: []int{1, 2, 3},
36+
k: 5,
37+
want: []int{2, 3, 1},
38+
},
39+
{
40+
name: "k is zero",
41+
nums: []int{1, 2, 3, 4},
42+
k: 0,
43+
want: []int{1, 2, 3, 4},
44+
},
45+
{
46+
name: "single element array",
47+
nums: []int{1},
48+
k: 3,
49+
want: []int{1},
50+
},
51+
{
52+
name: "two element array rotate by 1",
53+
nums: []int{1, 2},
54+
k: 1,
55+
want: []int{2, 1},
56+
},
57+
{
58+
name: "rotate by 1",
59+
nums: []int{1, 2, 3, 4, 5},
60+
k: 1,
61+
want: []int{5, 1, 2, 3, 4},
62+
},
63+
{
64+
name: "rotate entire array multiple times",
65+
nums: []int{1, 2, 3},
66+
k: 9,
67+
want: []int{1, 2, 3},
68+
},
69+
{
70+
name: "array with negative numbers",
71+
nums: []int{-5, -3, -1, 0, 2, 4},
72+
k: 2,
73+
want: []int{2, 4, -5, -3, -1, 0},
74+
},
75+
{
76+
name: "array with duplicates",
77+
nums: []int{1, 1, 2, 2, 3, 3},
78+
k: 3,
79+
want: []int{2, 3, 3, 1, 1, 2},
80+
},
81+
{
82+
name: "large k value",
83+
nums: []int{1, 2, 3, 4, 5},
84+
k: 100003,
85+
want: []int{3, 4, 5, 1, 2},
86+
},
87+
}
88+
89+
for _, tt := range tests {
90+
t.Run(tt.name, func(t *testing.T) {
91+
// Make a copy since rotate modifies in-place
92+
nums := make([]int, len(tt.nums))
93+
copy(nums, tt.nums)
94+
95+
rotate(nums, tt.k)
96+
97+
if !reflect.DeepEqual(nums, tt.want) {
98+
t.Errorf("rotate() = %v, want %v", nums, tt.want)
99+
}
100+
})
101+
}
102+
}
103+
104+
func TestReverse(t *testing.T) {
105+
tests := []struct {
106+
name string
107+
nums []int
108+
want []int
109+
}{
110+
{
111+
name: "reverse odd length array",
112+
nums: []int{1, 2, 3, 4, 5},
113+
want: []int{5, 4, 3, 2, 1},
114+
},
115+
{
116+
name: "reverse even length array",
117+
nums: []int{1, 2, 3, 4},
118+
want: []int{4, 3, 2, 1},
119+
},
120+
{
121+
name: "reverse single element",
122+
nums: []int{1},
123+
want: []int{1},
124+
},
125+
{
126+
name: "reverse two elements",
127+
nums: []int{1, 2},
128+
want: []int{2, 1},
129+
},
130+
{
131+
name: "reverse empty array",
132+
nums: []int{},
133+
want: []int{},
134+
},
135+
}
136+
137+
for _, tt := range tests {
138+
t.Run(tt.name, func(t *testing.T) {
139+
nums := make([]int, len(tt.nums))
140+
copy(nums, tt.nums)
141+
142+
reverse(nums)
143+
144+
if !reflect.DeepEqual(nums, tt.want) {
145+
t.Errorf("reverse() = %v, want %v", nums, tt.want)
146+
}
147+
})
148+
}
149+
}

0 commit comments

Comments
 (0)