Golang Go语言中协程请求数据
我一个接口里边,需要多次操作数据库,现在想通过协程来实现。 下边这个 demo 是一个样例, 我在 resp 怎么区分协程的返回值,这里边还有些不太清晰。
func main() {
var ch = make(chan []byte)
go request("https://www.baidu.com", ch)
go request("https://www.taobao.com", ch)
go request("https://www.google.com", ch)
i := 0
timer := time.NewTimer(time.Second * 3)
L:
for {
select {
case <-timer.C:
break L
case resp := <-ch:
fmt.Printf("%d\n", len(resp))
// 接收 3 个之后关闭 chan
i++
if i == 3 {
close(ch)
break L
}
}
}
// more code…
}
Golang Go语言中协程请求数据
更多关于Golang Go语言中协程请求数据的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
你是要区分每个协程的返回值吗?不同的协程对应不同处理方式?
那么再构建一个一个结构体,例如:
type CRes struct {
}
更多关于Golang Go语言中协程请求数据的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
你是要区分每个协程的返回值吗?不同的协程(或者说:不同的数据库)对应不同处理方式?
那么再构建一个一个结构体,例如:
type CRes struct {
ChannelType int // taobao:1, baidu:2, google:3
Res interfact{}
}
ch := make(chan CRes)
每个协程函数返回 CRes ,然后将 CRes 返回到 channel 中。在接受、处理 channel 的函数中,根据不同的 channelType 进行处理
明白了,谢谢你。
我修改后的 demo 发下
package main
import (
“fmt”
“time”
)
type CRes struct {
ChannelType int
Res interface{}
}
func main() {
var ch = make(chan CRes)
go test1(ch)
go test2(ch)
for i := 0; i < 2; i++ {
select {
case <-time.After(time.Second * 5):
fmt.Println(“超时操作”)
break
case resp := <-ch:
if resp.ChannelType == 1 {
fmt.Printf(“这是 1 的数据”)
}
if resp.ChannelType == 2 {
fmt.Printf(“这是 2 的数据”)
}
break
default:
fmt.Println(“资源已满,请稍后再试”)
}
}
}
func test1(ch chan CRes) {
res := CRes{
ChannelType: 1,
Res: nil,
}
ch <- res
}
func test2(ch chan CRes) {
res := CRes{
ChannelType: 2,
Res: nil,
}
ch <- res
}
md5(url) 作为任务的 ID ,返回的时候也对应的带上这个 ID 。
context 带个 id 进去
没必要这么复杂吧,直接用 errgroup 。最近有个协程的库看起来还可以 https://github.com/sourcegraph/conc
在Go语言中,协程(goroutine)是一种轻量级的线程,由Go运行时管理,用于并发执行任务。使用协程请求数据是一种常见的并发编程模式,可以显著提高程序的性能和响应速度。
当你需要在Go中使用协程请求数据时,通常会用到net/http
包来发起HTTP请求。以下是一个简单的示例,展示了如何使用协程来并发地请求多个URL的数据:
package main
import (
"fmt"
"io/ioutil"
"net/http"
"sync"
)
func fetchData(url string, wg *sync.WaitGroup, results chan<- string) {
defer wg.Done()
resp, err := http.Get(url)
if err != nil {
results <- fmt.Sprintf("Error fetching %s: %v", url, err)
return
}
defer resp.Body.Close()
body, err := ioutil.ReadAll(resp.Body)
if err != nil {
results <- fmt.Sprintf("Error reading response from %s: %v", url, err)
return
}
results <- fmt.Sprintf("Data from %s: %s", url, body)
}
func main() {
var wg sync.WaitGroup
results := make(chan string, 10)
urls := []string{"http://example.com", "http://another-example.com"}
for _, url := range urls {
wg.Add(1)
go fetchData(url, &wg, results)
}
wg.Wait()
close(results)
for result := range results {
fmt.Println(result)
}
}
这个示例中,我们使用了sync.WaitGroup
来等待所有协程完成,并使用一个通道results
来收集每个协程的结果。这样,你就可以并发地请求多个URL的数据,并在所有请求完成后处理结果。