Home > Enterprise >  How to execute the `case` in the `select` statement only if some conditions are satisfied
How to execute the `case` in the `select` statement only if some conditions are satisfied

Time:11-20

I have a channel:

aChan := make(chan struct{})

and a timeout duration var t time.Duration. I want the program to exit either if the channel is closed, or the t timeout is reached, if t is a positive duration.

I know I can use an outer if else loop, but this looks very redundant:

    if t >= time.Duration(0) {
        select {
        case <-time.After(t):
            fmt.Fprintln(os.Stdout, "timeout!"))
            close(timeoutChan)
        case <-aChan:
            fmt.Fprintln(os.Stdout, "aChan is closed"))
            return
        }
    } else {
        select {
        case <-aChan:
            fmt.Fprintln(os.Stdout, "aChan is closed"))
            return
        }
    }

Is there a more elegant way to write this?

CodePudding user response:

Use a nil channel for the timeout when the duration is less than zero. The timeout case with a nil channel is not executed because receive on a nil channel is never ready.

var after <-chan time.Time
if t >= 0 {
    after = time.After(t)
}
select {
case <-after:
    fmt.Println("timeout!")
    close(timeoutChan)
case <-aChan:
    fmt.Println("aChan is closed")
    return
}
  • Related