package main
import (
"fmt"
"time"
)
func worker(done chan bool) {
fmt.Println("working...")
time.Sleep(time.Second)
fmt.Println("done")
done <- true // 写入信息到管道内
}
func ping(pings chan<- string, msg string) {
// 这里pings是输入
pings <- msg
}
func pong(pings <-chan string, pongs chan<- string) {
msg := <-pings // 这里pings是输出
pongs <- msg
}
func main() {
message := make(chan string) // 传建一个频道管道,内容类型是字符串
go func() { message <- "ping" }() // 执行发送ping到管道上
msg := <-message // 接收管理上的值并赋值给msg
fmt.Println(msg) // 打印管道内容
// 缓冲两个值
msg2 := make(chan string, 2) // 设置两个对话的管道
msg2 <- "buffered" // 发送信息到管道
msg2 <- "channel"
fmt.Println(<-msg2) // 取出信息
fmt.Println(<-msg2)
// 通知工作完成
done := make(chan bool, 1)
go worker(done)
<-done // 获取管道信息
// 发送和接收
pings := make(chan string, 1)
pongs := make(chan string, 1)
ping(pings, "hello chan") // 输入pings接收方管道
pong(pings, pongs) // 从接收方管道读取输出到结果方管道
fmt.Println(<-pongs) // 从结果管理取出数据
// 获取异步信息
c1 := make(chan string)
c2 := make(chan string)
go func() {
time.Sleep(2 * time.Second)
c1 <- "hello11" // 输入两次,则可读取两次
c1 <- "hello22"
}()
go func() {
time.Sleep(1 * time.Second)
c2 <- "world"
}()
for i := 0; i < 2; i++ {
select {
case msg1 := <-c1:
fmt.Println("received1", msg1)
case msg2 := <-c2:
fmt.Println("received2", msg2)
}
}
fmt.Println("received1 out", <-c1) // <-里面如果为空只会报错
// 超时,一个超时一个不超时的例子
c3 := make(chan string, 1)
go func() {
time.Sleep(2 * time.Second)
c3 <- "result 1"
}()
select {
case res := <-c3:
fmt.Println(res)
case <-time.After(1 * time.Second): // 超时1s
fmt.Println("timeout 1")
}
c4 := make(chan string, 1)
go func() {
time.Sleep(2 * time.Second)
c4 <- "result 2"
}()
select {
case res := <-c4:
fmt.Println(res)
case <-time.After(time.Second * 3):
fmt.Println("timeout 2")
}
// 使用default实现非阻塞,不写默认处理会阻塞成为死锁。
msg5 := make(chan string)
signals := make(chan string)
select {
case msg := <-msg5:
fmt.Println(msg)
default:
fmt.Println("no msg received")
}
msgStr1 := "hi"
select {
case msg5 <- msgStr1:
fmt.Println("sent message", msg)
default:
fmt.Println("no meg sent")
}
select {
case msg := <-msg5:
fmt.Println("receive msg", msg)
case sig := <-signals:
fmt.Println("receive signal", sig)
default:
fmt.Println("no activity")
}
// 关闭管道:表示不会在其上发送更多值
jobs := make(chan int, 5)
done2 := make(chan bool)
go func() {
for { // 一直监听jobs的值
j, more := <-jobs
if more {
fmt.Println("received job", j)
} else {
fmt.Println("receive all jobs")
done2 <- true
return
}
}
}()
for i := 0; i < 3; i++ {
jobs <- i // 发送值给jobs
fmt.Println("sent job", i)
}
close(jobs) // 关闭管道,发送完毕
fmt.Println("sent all jobs")
<-done2
// 缓存管道
queue := make(chan string, 2)
queue <- "one"
queue <- "two"
close(queue)
for elem := range queue {
fmt.Println("elem", elem)
}
// 定时器
timer := time.NewTimer(2 * time.Second)
<-timer.C
fmt.Println("Time. 1 fired")
timer2 := time.NewTimer(time.Second)
go func() {
<-timer2.C
fmt.Println("timer2 2 fired")
}()
stop2 := timer2.Stop()
if stop2 {
fmt.Println("t2 stop", stop2)
}
time.Sleep(2 * time.Second)
// 延时器
ticker := time.NewTicker(500 * time.Microsecond)
done4 := make(chan bool)
go func() {
for { // 内部循环,终止循环的钥匙放在另一个管理里面。
select {
case <-done4:
return
case t := <-ticker.C:
fmt.Println("tick at", t)
}
}
}()
time.Sleep(1600 * time.Millisecond)
ticker.Stop()
done4 <- true // 类似于 resolve(true), 来当做是一个停止管理去操作
fmt.Println("ticker stopped")
}
go-基础-channels
最新推荐文章于 2023-05-14 23:02:20 发布