协程 go 函数 相互独立运行的能力。 Goroutines是并发运行的函数
创建语法
实例1 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 package mainimport ( "fmt" "time" ) func f1 (s string ) { for i := 0 ; i < 10 ; i++ { fmt.Printf("第%d次执行 %v \n" , i + 1 , s) time.Sleep(time.Millisecond * 100 ) } } func main () { go f1("test" ) f1("test2" ) fmt.Println("over" ) }
通道 channel 用于在协程之间共享数据 作为协程之间的管道保证通信同步 需要在声明通道时指定数据类型 任何给定时间都只有一个能访问通道
通道由make函数创建,该函数指定chan关键字和通道的元素类型
创建语法 1 2 3 4 5 Unbuffered := make (chan int ) buffered := make (chan string , 10 )
发送接受语法 1 2 3 4 5 6 7 var myChannel = make (chan string )var s string myChannel <- s s <- myChannel
WaitGroup实现同步 实例 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 package mainimport ( "fmt" "sync" ) var wg sync.WaitGroupfunc say (i int ) { defer wg.Done() fmt.Printf("这是第%d\n" , i + 1 ) } func main () { for i := 0 ; i < 10 ; i++ { go say(i) wg.Add(1 ) } wg.Wait() }
Mutext 互斥锁 实例 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 package mainimport ( "fmt" "sync" "time" ) var wg sync.WaitGroupvar lock sync.Mutexvar res = 100 func add () { defer wg.Done() res += 1 time.Sleep(time.Millisecond * 10 ) } func sub () { defer wg.Done() res -= 1 time.Sleep(time.Millisecond * 10 ) } func main () { for i := 0 ; i < 100 ; i++ { go add() wg.Add(1 ) go sub() wg.Add(1 ) } wg.Wait() fmt.Print(res) }
select
类似于switch 用于处理异步IO操作。select会监听case中channel的读写操作,当case中的channel读写操作为非堵塞 状态时会触发相应动作
如果多个case都可以运行,则会随机选择一个执行
如果没有default语句,且没有可执行case语句,select将会堵塞
实例 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 package mainimport ( "fmt" "time" ) var chanInt = make (chan int )var chanStr = make (chan string )func main () { go func () { chanInt <- 1 }() go func () { chanStr <- "test" }() for { select { case r := <-chanInt: fmt.Printf("%v\n" , r) case r := <-chanStr: fmt.Printf("%v\n" , r) default : fmt.Println("none" ) } time.Sleep(time.Second) } }