Remove Elements from a Slice Iteratively
When iterating over a slice, removing an element within the loop can be tricky due to the shifting of subsequent elements. A common incorrect approach is using append to remove an element, as seen in the example below:
a := []string{"abc", "bbc", "aaa", "aoi", "ccc"}
for i := range a { // BAD
if conditionMeets(a[i]) {
a = append(a[:i], a[i 1:]...)
}
}
This method does not work correctly because the loop does not account for the shifted elements. To properly remove elements while iterating, you can either use a downward loop or employ an alternative method that avoids constant copy operations.
Downward Loop
A downward loop iterates in reverse order, starting from the last element. This approach allows you to remove elements without having to manually decrement loop variables:
a := []string{"abc", "bbc", "aaa", "aoi", "ccc"}
for i := len(a) - 1; i >= 0; i-- {
if conditionMeets(a[i]) {
a = append(a[:i], a[i 1:]...)
}
}
Alternate Method for Many Removals
If you need to remove a large number of elements, using append can be inefficient due to excessive copying. An alternative approach is to create a new slice and copy only the non-removable elements:
a := []string{"abc", "bbc", "aaa", "aoi", "ccc"}
b := make([]string, len(a))
copied := 0
for _, s := range(a) {
if !conditionMeets(s) {
b[copied] = s
copied
}
}
b = b[:copied]
In-Place Removal for Many Removals (General Purpose)
An in-place removal technique involves maintaining two indices and assigning non-removable elements in the same slice while zeroing out removed element locations:
a := []string{"abc", "bbc", "aaa", "aoi", "ccc"}
copied := 0
for i := 0; i
Disclaimer: All resources provided are partly from the Internet. If there is any infringement of your copyright or other rights and interests, please explain the detailed reasons and provide proof of copyright or rights and interests and then send it to the email: [email protected] We will handle it for you as soon as possible.
Copyright© 2022 湘ICP备2022001581号-3