multithreading - Go-尝试创建超过一定数量的goroutine时出现段错误问题

标签 multithreading go concurrency goroutine

我试图在go中对http客户端进行压力测试。
一开始,我只是尝试运行10个并发请求10次迭代。
这是我的客户代码:

// stress.go
package main

import (
    "fmt"
    "io/ioutil"
    "net/http"
    "time"
)

func MakeRequest(url string, ch chan<- string) {
    start := time.Now()
    resp, _ := http.Get(url)

    secs := time.Since(start).Seconds()
    body, _ := ioutil.ReadAll(resp.Body)
    ch <- fmt.Sprintf("%.2f elapsed with response length: %d %s", secs, len(body), url)
}

func main() {
    start := time.Now()
    goroutines := 10
    iterations := 10
    ch := make(chan string)
    url := "http://localhost:8000"
    for i := 0; i < iterations; i++ {
        for j := 0; j < goroutines; j++ {
            go MakeRequest(url, ch)
        }
    }
    for i := 0; i < goroutines*iterations; i++ {
        fmt.Println(<-ch)
    }

    fmt.Printf("%.2fs elapsed\n", time.Since(start).Seconds())
}

对于迭代和goroutine的这种组合,它工作得很好。但是,当goroutine和迭代次数超过某个级别时,在我的例子中,对于单个迭代,当goroutine的次数超过634时,我收到这个错误:
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x48 pc=0x11eb9f0]

goroutine 7099 [running]:
main.MakeRequest(0x1271897, 0x15, 0xc420074120)
        stress.go:16 +0xa0
                created by main.main
                        stress.go:28 +0xb2

根据this,可以轻松创建10000个goroutine。我在我的案子里做错了什么?如何测试客户机在给定迭代次数下并发发出的get或post请求的最大数量?

最佳答案

您正在丢弃http.get和ioutil.readall中的错误,所以您得到一个nil指针解引用并不奇怪;如果这不是一个有效的假设,您假设返回值是好的。服务器可能返回错误,因为您已超过服务器的最大吞吐量。
您也没有在10次迭代中测试10个goroutine,而是在测试100个goroutine;并且在读完请求体之后,也没有关闭它们。最后,您可以获得多少吞吐量将取决于服务器、服务器有多少可用资源以及客户端有多少可用资源;以及两者之间的竞争,由于您正在访问本地主机,客户机和服务器正在争夺相同的系统资源。
任何语言都没有静态性能特性;它取决于运行它的上下文。

关于multithreading - Go-尝试创建超过一定数量的goroutine时出现段错误问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46386186/

相关文章:

c++ - openMP 缺乏 yield 递减与更高的线程数

sql-server - MS SQL 限制选项不起作用

go - 声明和初始化的简写在go lang中是如何计算的?

perl DBI 和准备好的语句名称冲突

java - 如何在并发环境中设计到数据库的http连接(是否为静态变量)

multithreading - 从后台线程更新 NSTableView 数据源

php - PHP 中的多线程编程以避免运行时限制

java - 在这种情况下,正确的 Java 集合是什么?

docker - 为什么执行 Golang 可执行文件的 docker 容器在启动后立即挂起?

java - 阻塞还会导致线程饥饿吗?