《GO語言高級編程》設計中案例,僅作爲筆記進行收藏。
package main
import (
"context"
"fmt"
)
// 返回生成自然數序列的管道:2,3,4……
func GenerateNatural(ctx context.Context) chan int {
ch := make(chan int)
go func() {
for i := 2; ; i++ {
// fmt.Printf("GenerateNatural:%v\n", i)
select {
case <-ctx.Done():
return
case ch <- i:
}
}
}()
return ch
}
// 管道過濾器:刪除能被素數正常的數
func PrimeFileter(ctx context.Context, in <-chan int, prime int) chan int {
out := make(chan int)
go func() {
for {
// fmt.Printf("PrimeFileter-prime:%v\n", prime)
if i := <-in; i%prime != 0 {
// fmt.Printf("PrimeFileter-if:%v\n", i)
select {
case <-ctx.Done():
return
case out <- i:
}
}
// fmt.Printf("PrimeFileter-for:%v\n", <-in)
}
}()
return out
}
func main() {
// 通過 Context 控制後臺 Goroutine狀態
ctx, cancel := context.WithCancel(context.Background())
// 自然數序列:2,3,4,……
ch := GenerateNatural(ctx)
for i := 0; i < 10; i++ {
// 新出現的素數
prime := <-ch
fmt.Printf("%v:%v\n", i+1, prime)
// 基於新素數構造的過濾器
// 如果未產生新的素數,則通道 ch 爲 nil;如果通道 ch 爲 nil,則 GenerateNatural 生成新的自然數,發送給ch,則PrimeFileter 過濾,直到通道不爲nil
ch = PrimeFileter(ctx, ch, prime)
}
cancel()
}
GenerateNatural 函數內部啓動⼀個Goroutine⽣產序列,返回對應的管道。
PrimeFilter 函數內部啓動⼀個Goroutine將輸入序列中是素數倍數的數提出,並返回新的序列,是⼀個新的
管道。
GenerateNatural 生產,PrimeFilter 過濾。逐步提取出素數。