3 ms·
That kind of suffers if you want to be able to cheaply cancel the iteration. Lets say the logic is: for item := range list { if condition(item) {
by liquidgecka 3y ago
That kind of suffers if you want to be able to cheaply cancel the iteration.
Lets say the logic is:
for item := range list {
if condition(item) {
break
}
}
That is nice and readable, but if the thing your iterating is returning items in a batch then this gets far, far uglier. Its possible to end up with one loop that fetches x items at a time, and another that iterates over those items.. etc. But if you switch that to channels you maintain the readability and everything is nice! .. Except, you need a way to cancel the iteration, and it can't be closing the channel or the writer will panic.
items, cancelFunc := apiCall()
for item := range items {
if condition(items) {
cancelFunc()
for _ := range items { }
break
}
}
close(items)
Now, this is even worse if you need some kind of finalization of the goroutine that spawns to write to the given channel. Now you have a wait group, or a second channel.. etc. If its possible to error in the middle of iteration then things get complicated as well.
- jppittma 3y agoI may not understand what you're looking for, but what's wrong with this: topLoop: for _, batch := range list { for _, item := range batch { if condition(item) { break topLoop } } } The language also supports a limited goto. Combined with select and context, I've never seen a situation I felt I couldn't adequately describe.