要考虑这样一个场景,一个线程不停生产数据,另一个线程不停消耗数据,这样的场景用channel最是方便。原先看到的channel都是传递基本数据类型的,如果传递更复杂的担心有问题。于是模拟了下面的程序
GenerateData用来生产一个比较复杂的数据,
RecvData用来接受生产出来的数据,收到后打印出来。
程序在一开始时先创建一个channel结构的变量c, 然后用go GenerateData创建生产数据的线程,再用go RecvData创建接收数据的线程,从打印结果看,收到的是一个指针,原始的数据应该还在生产者那里。
package main
import (
"fmt"
"time"
)
type MyWar struct {
code int
id int
}
type MyData struct{
age int
wars []MyWar
}
func RecvData(c chan *MyData) {
for {
data := <-c
fmt.Printf("%v\n", data)
}
}
func GenerateData(c chan *MyData) {
var times int
for {
times++
count := times % 4
myData := new(MyData)
myData.age = 15
myData.wars = make([]MyWar, count)
for i := 0; i < count; i++ {
myData.wars[i].code = (i+1)*10
myData.wars[i].id = i
}
c <- myData
time.Sleep(time.Second)
}
}
func main() {
c := make(chan *MyData)
go GenerateData(c)
go RecvData(c)
var input string
fmt.Scanln(&input)
}
打印结果:
&{15 []}
&{15 [{10 0}]}
&{15 [{10 0} {20 1}]}
&{15 [{10 0} {20 1} {30 2}]}
&{15 []}
&{15 [{10 0}]}
......