我如何杀死一个协程
How do I kill a goroutine
我有以下设置:
func startsMain (){
go main ()
}
fun stopMain (){
//kill main
}
func main() {
//infinite loop
}
我正在创建黄瓜步骤,我需要能够启动和关闭应用程序。
您可以使用 select
和频道来结束无限循环!
var quit chan struct{}
func startLoop() {
quit := make(chan struct{})
go loop()
}
func stopLoop() {
// As mentioned by Kaedys
//close(quit)
// permits signalling everyone havins such a `case <-quit:`
// statement to be stopped at once, which might be even better.
quit <- struct{}{}
}
// BTW, you cannot call your function main, it is reserved
func loop() {
for {
select {
case <-quit:
return # better than break
default:
// do stuff. I'd call a function, for clarity:
do_stuff()
}
}
}
很好的 Go 交换,不是吗?
现在,这有什么奇怪的 chan struct{}
?它是一个零大小的通道。我们只能用空结构填充它(即:struct{}{}
)。它可以是 chan bool
或其他任何内容,因为我们不使用频道的内容。重要的一点是我们使用 quit
通道通知我们的 goroutine 中的无限循环是时候停止了。
select
语句用于捕获来自通道的内容。这是一个阻塞语句(它将停止执行,直到将某些内容放入 case
调查的通道之一),除非您放置 default
语句。在这种情况下,每次执行 select
时,如果在 quit
中放入了某些内容,循环就会中断,或者会调用 do_stuff()
。如果您经历过 Go Tour.
,您已经知道这一点
可以在 Go Blog.
上找到其他很酷的并发模式
最后,为了更有趣,您可以使用 Ticker
s 要求您的 do_stuff
函数定期执行,而不是像这样消耗 100% CPU :
import "time"
// [...]
func loop() {
// This ticker will put something in its channel every 2s
ticker := time.NewTicker(2 * time.Second)
// If you don't stop it, the ticker will cause memory leaks
defer ticker.Stop()
for {
select {
case <-quit:
return
case <-ticker.C:
// do stuff. I'd call a function, for clarity:
do_stuff()
}
}
}
此处,select
处于阻塞状态,因为我们删除了 default
语句。
我有以下设置:
func startsMain (){
go main ()
}
fun stopMain (){
//kill main
}
func main() {
//infinite loop
}
我正在创建黄瓜步骤,我需要能够启动和关闭应用程序。
您可以使用 select
和频道来结束无限循环!
var quit chan struct{}
func startLoop() {
quit := make(chan struct{})
go loop()
}
func stopLoop() {
// As mentioned by Kaedys
//close(quit)
// permits signalling everyone havins such a `case <-quit:`
// statement to be stopped at once, which might be even better.
quit <- struct{}{}
}
// BTW, you cannot call your function main, it is reserved
func loop() {
for {
select {
case <-quit:
return # better than break
default:
// do stuff. I'd call a function, for clarity:
do_stuff()
}
}
}
很好的 Go 交换,不是吗?
现在,这有什么奇怪的 chan struct{}
?它是一个零大小的通道。我们只能用空结构填充它(即:struct{}{}
)。它可以是 chan bool
或其他任何内容,因为我们不使用频道的内容。重要的一点是我们使用 quit
通道通知我们的 goroutine 中的无限循环是时候停止了。
select
语句用于捕获来自通道的内容。这是一个阻塞语句(它将停止执行,直到将某些内容放入 case
调查的通道之一),除非您放置 default
语句。在这种情况下,每次执行 select
时,如果在 quit
中放入了某些内容,循环就会中断,或者会调用 do_stuff()
。如果您经历过 Go Tour.
可以在 Go Blog.
上找到其他很酷的并发模式最后,为了更有趣,您可以使用 Ticker
s 要求您的 do_stuff
函数定期执行,而不是像这样消耗 100% CPU :
import "time"
// [...]
func loop() {
// This ticker will put something in its channel every 2s
ticker := time.NewTicker(2 * time.Second)
// If you don't stop it, the ticker will cause memory leaks
defer ticker.Stop()
for {
select {
case <-quit:
return
case <-ticker.C:
// do stuff. I'd call a function, for clarity:
do_stuff()
}
}
}
此处,select
处于阻塞状态,因为我们删除了 default
语句。