Common slice operations in Go - Time & Space Complexity
When working with slices in Go, it's important to know how the time needed changes as the slice grows.
We want to understand how common slice actions take longer or stay the same as the slice gets bigger.
Analyze the time complexity of the following code snippet.
// Append elements to a slice
func appendElements(slice []int, n int) []int {
for i := 0; i < n; i++ {
slice = append(slice, i)
}
return slice
}
// Access element by index
func accessElement(slice []int, index int) int {
return slice[index]
}
This code shows two common slice operations: adding elements one by one and accessing an element by its position.
Identify the loops, recursion, array traversals that repeat.
- Primary operation: The loop that appends elements to the slice.
- How many times: The loop runs n times, once for each element added.
- Accessing an element by index happens just once, no repetition.
As the number of elements n increases, the time to append grows roughly in direct proportion.
| Input Size (n) | Approx. Operations |
|---|---|
| 10 | About 10 append steps |
| 100 | About 100 append steps |
| 1000 | About 1000 append steps |
Accessing an element by index takes the same small amount of time no matter the size.
Pattern observation: Appending grows linearly, accessing stays constant.
Time Complexity: O(n) for appending elements, O(1) for accessing an element.
This means adding many elements takes longer as you add more, but getting one element is always quick.
[X] Wrong: "Appending one element to a slice always takes the same tiny time no matter what."
[OK] Correct: Sometimes appending triggers the slice to grow its storage, which takes extra time, so appending many elements adds up.
Understanding how slice operations scale helps you write efficient code and explain your choices clearly in conversations.
"What if we changed the append loop to add elements in batches instead of one by one? How would the time complexity change?"
Practice
mySlice[2:5] do in Go?Solution
Step 1: Understand slice syntax
The slice expressionmySlice[2:5]extracts elements starting at index 2 up to, but not including, index 5. Go slices use half-open intervals, so the element at index 5 is not included in the new slice.Final Answer:
It returns a new slice containing elements from index 2 up to, but not including, index 5. -> Option AQuick Check:
Slice[start:end] excludes end index [OK]
- Including the end index element in the slice
- Thinking slice removes elements from original
- Confusing append with slicing
5 to a slice nums in Go?Solution
Step 1: Recall append function usage
In Go,appendreturns a new slice with the element added, so you must assign it back.nums = append(nums, 5)correctly assigns the result back tonums.append(nums, 5)ignores the returned slice.nums.append(5)uses invalid method syntax.nums += 5is invalid for slices.Final Answer:
nums = append(nums, 5) -> Option DQuick Check:
append returns new slice, assign it [OK]
- Not assigning append result back
- Using method syntax like nums.append()
- Trying to add with += operator
nums := []int{1, 2, 3, 4, 5}
slice := nums[1:4]
slice[0] = 10
fmt.Println(nums)Solution
Step 1: Understand slice referencing
The sliceslice := nums[1:4]references the original array elements at indexes 1, 2, and 3. Changingslice[0]to 10 changesnums[1]because slices share the underlying array. Output: [1 10 3 4 5]Final Answer:
[1 10 3 4 5] -> Option AQuick Check:
Slices share array, modifying slice changes original [OK]
- Thinking slice is a copy, not a reference
- Modifying wrong index in slice
- Confusing slice length with capacity
nums := []int{1, 2, 3}
newSlice := nums[1:4]
fmt.Println(newSlice)Solution
Step 1: Check slice bounds
The original slicenumshas length 3, so valid indices are 0 to 2. Attemptingnums[1:4]tries to access index 3 which is out of range, causing a runtime panic.Final Answer:
Slicing beyond the slice length causes a runtime panic. -> Option CQuick Check:
Slice end index must be ≤ length [OK]
- Assuming slice auto-expands
- Confusing compile error with runtime panic
- Ignoring slice length when slicing
data := []int{2, 4, 6, 8, 10, 12}, how can you create a new slice containing only the even numbers greater than 6 using slicing and append?Solution
Step 1: Identify elements > 6
Elements greater than 6 are 8, 10, 12 at indexes 3, 4, 5. Usingdata[3:]gets these elements. To create a new slice (not referencing original), append to empty slice:newSlice := append([]int{}, data[3:]...).Final Answer:
newSlice := append([]int{}, data[3:]...) -> Option BQuick Check:
Slice and append to copy subset [OK]
- Using slice without append copies reference
- Incorrect slice indexes for desired elements
- Trying to remove elements by slicing incorrectly
Ready to prove it?
Pass the test and this pattern moves unknown
