Skip to content

Instantly share code, notes, and snippets.

@robot-dreams
Last active February 16, 2018 10:31
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save robot-dreams/de547bbd0468e16333229316fad4c51a to your computer and use it in GitHub Desktop.
Save robot-dreams/de547bbd0468e16333229316fad4c51a to your computer and use it in GitHub Desktop.
Useful pattern from "Concurrency in Go" for merging "done" channels
// Returns a channel that will be closed whenever ANY of the input channels are
// closed (or written to).
func or(channels ...<-chan struct{}) <-chan struct{} {
switch len(channels) {
case 0:
return nil
case 1:
return channels[0]
}
orDone := make(chan struct{})
go func() {
defer close(orDone)
switch len(channels) {
case 2:
select {
case <-channels[0]:
case <-channels[1]:
}
default:
select {
case <-channels[0]:
case <-channels[1]:
case <-channels[2]:
case <-or(append(channels[3:], orDone)...):
}
}
}()
return orDone
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment