Looping and tail-end code

127 views
Skip to first unread message

Tobias Klausmann

unread,
Jan 12, 2022, 5:03:01 AM1/12/22
to golan...@googlegroups.com
Hi!

Often with tools that poll something, you get code of this form:

```
for {
r, err := doSomeCall()
if err != nil {
log.Printf("Some error:", err)
continue
}
s, err := doSomeOtherCall(r)
if err != nil {
log.Printf("Some other error:", err)
continue
}
}
```

This works nice and dandy, except that it of course runs as fast/hard as
it can, so usually, one would have a `time.Sleep()` or something like it
at the end of the `for{}`. Except: now the error handling blocks can't
use `continue` anymore. I can of course make this a nested set of
`if {} else {}` blocks, but beyond two calls, that is very ugly and hard
to understand.

So what is the *idiomatic* way of being able to use `continue` (or
something like it), yet have "always do this" code at the end of the
loop? As I understand it, `defer` only works for ends of functions, not
ends of blocks, and label breaks only work for breaks, obviously.

Best,
Tobias

Rob Pike

unread,
Jan 12, 2022, 6:40:24 AM1/12/22
to golan...@googlegroups.com
What's wrong with
for ;; time.Sleep(delay) { ... }
?

This technique is as old as the hills. Or at least as old as C for loops.

-rob
> --
> You received this message because you are subscribed to the Google Groups "golang-nuts" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts...@googlegroups.com.
> To view this discussion on the web visit https://groups.google.com/d/msgid/golang-nuts/Yd6nL/ScO9gO0TgB%40skade.schwarzvogel.de.

Tobias Klausmann

unread,
Jan 12, 2022, 10:04:17 AM1/12/22
to golan...@googlegroups.com
Hi!

On Wed, 12 Jan 2022, Rob Pike wrote:
> What's wrong with
> for ;; time.Sleep(delay) { ... }
> ?
>
> This technique is as old as the hills. Or at least as old as C for loops.

Never been a C guy :) Thanks, that works perfectly!

Best,
Tobias

David Finkel

unread,
Jan 12, 2022, 11:04:48 AM1/12/22
to golang-nuts
On Wed, Jan 12, 2022 at 5:02 AM Tobias Klausmann <klau...@schwarzvogel.de> wrote
 
So what is the *idiomatic* way of being able to use `continue` (or
something like it), yet have "always do this" code at the end of the
loop? As I understand it, `defer` only works for ends of functions, not
ends of blocks, and label breaks only work for breaks, obviously.
 
I generally pull the bulk of the loop body into another function/method (usually called tick()) that I call inside the loop just before sleeping.
 (or more typically, a select{} block checking a ticker and a context)

(I like Rob's option, too. -- although that doesn't work with select{} blocks as well) 
Reply all
Reply to author
Forward
0 new messages