Created
November 25, 2021 15:11
-
-
Save aldy505/f8e83b6fbab624c8c3907be6d07ed843 to your computer and use it in GitHub Desktop.
Simple yet annoying demonstration of concurrency stuffs in Go
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package main | |
import ( | |
"fmt" | |
"log" | |
"sync" | |
"time" | |
) | |
func main() { | |
withMachine := Machines{} | |
orders := make(chan int, 12) | |
for i := 0; i < 12; i++ { | |
go withMachine.makeCoffee(orders, i+1) | |
} | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Order completed for order no.", <-orders) | |
fmt.Println("Espresso machine, time used:", withMachine.EspressoMachine.TimeUsed) | |
fmt.Println("Beans grinder, time used:", withMachine.BeansGrinder.TimeUsed) | |
} | |
type EspressoMachine struct { | |
sync.Mutex | |
InUse bool | |
TimeUsed int | |
} | |
type BeansGrinder struct { | |
sync.Mutex | |
InUse bool | |
TimeUsed int | |
} | |
type Machines struct { | |
BeansGrinder | |
EspressoMachine | |
} | |
func (m *Machines) makeCoffee(orders chan int, number int) { | |
log.Printf("Got order number %d\n", number) | |
var wg sync.WaitGroup | |
wg.Add(3) | |
prepare := make(chan bool, 2) | |
go prepareGlass(wg, prepare, number) | |
go m.BeansGrinder.roastBeans(wg, prepare, number) | |
<-prepare | |
<-prepare | |
close(prepare) | |
go m.EspressoMachine.makeEspresso(wg, number) | |
orders <- number | |
wg.Wait() | |
} | |
func prepareGlass(wg sync.WaitGroup, status chan bool, number int) { | |
log.Printf("Preparing glass for order no. %d\n", number) | |
time.Sleep(time.Second*1) | |
wg.Done() | |
status <- true | |
} | |
func (b *BeansGrinder) roastBeans(wg sync.WaitGroup, status chan bool, number int) { | |
b.Lock() | |
defer b.Unlock() | |
log.Printf("Roasting beans for order no. %d\n", number) | |
b.InUse = true | |
time.Sleep(time.Second*2) | |
b.InUse = false | |
b.TimeUsed++ | |
wg.Done() | |
status <- true | |
} | |
func (e *EspressoMachine) makeEspresso(wg sync.WaitGroup, number int) { | |
e.Lock() | |
defer e.Unlock() | |
log.Printf("Making espresso for order no. %d\n", number) | |
e.InUse = true | |
time.Sleep(time.Second*3) | |
e.InUse = false | |
e.TimeUsed++ | |
wg.Done() | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment