何個のゴルーチンを無痛で使用できますか? たとえばウィキペディアによると、Erlang では、パフォーマンスを低下させることなく 2000 万のプロセスを作成できます。
更新:ゴルーチンのパフォーマンスを少し調査したところ、次のような結果が得られました。
- ゴルーチンの寿命は sqrt() を 1000 回 (私にとっては ~45µs ) 計算するよりも長いようです。唯一の制限はメモリです
- ゴルーチンのコストは 4 — 4.5 KB
何個のゴルーチンを無痛で使用できますか? たとえばウィキペディアによると、Erlang では、パフォーマンスを低下させることなく 2000 万のプロセスを作成できます。
更新:ゴルーチンのパフォーマンスを少し調査したところ、次のような結果が得られました。
ゴルーチンがブロックされている場合、以下以外にコストはかかりません。
コスト (ゴルーチンの実行を実際に開始するためのメモリと平均時間に関して) は次のとおりです。
Go 1.6.2 (April 2016)
32-bit x86 CPU (A10-7850K 4GHz)
| Number of goroutines: 100000
| Per goroutine:
| Memory: 4536.84 bytes
| Time: 1.634248 µs
64-bit x86 CPU (A10-7850K 4GHz)
| Number of goroutines: 100000
| Per goroutine:
| Memory: 4707.92 bytes
| Time: 1.842097 µs
Go release.r60.3 (December 2011)
32-bit x86 CPU (1.6 GHz)
| Number of goroutines: 100000
| Per goroutine:
| Memory: 4243.45 bytes
| Time: 5.815950 µs
4 GB のメモリがインストールされているマシンでは、これによりゴルーチンの最大数が 100 万未満に制限されます。
ソース コード (上記の数値を既に理解している場合は、これを読む必要はありません):
package main
import (
"flag"
"fmt"
"os"
"runtime"
"time"
)
var n = flag.Int("n", 1e5, "Number of goroutines to create")
var ch = make(chan byte)
var counter = 0
func f() {
counter++
<-ch // Block this goroutine
}
func main() {
flag.Parse()
if *n <= 0 {
fmt.Fprintf(os.Stderr, "invalid number of goroutines")
os.Exit(1)
}
// Limit the number of spare OS threads to just 1
runtime.GOMAXPROCS(1)
// Make a copy of MemStats
var m0 runtime.MemStats
runtime.ReadMemStats(&m0)
t0 := time.Now().UnixNano()
for i := 0; i < *n; i++ {
go f()
}
runtime.Gosched()
t1 := time.Now().UnixNano()
runtime.GC()
// Make a copy of MemStats
var m1 runtime.MemStats
runtime.ReadMemStats(&m1)
if counter != *n {
fmt.Fprintf(os.Stderr, "failed to begin execution of all goroutines")
os.Exit(1)
}
fmt.Printf("Number of goroutines: %d\n", *n)
fmt.Printf("Per goroutine:\n")
fmt.Printf(" Memory: %.2f bytes\n", float64(m1.Sys-m0.Sys)/float64(*n))
fmt.Printf(" Time: %f µs\n", float64(t1-t0)/float64(*n)/1e3)
}
それは、実行しているシステムに完全に依存します。しかし、ゴルーチンは非常に軽量です。平均的なプロセスでは、100.000 の同時ルーチンで問題が発生することはありません。もちろん、これがターゲット プラットフォームに当てはまるかどうかは、そのプラットフォームが何であるかを知らずに答えることはできません。
言い換えれば、嘘、いまいましい嘘、ベンチマークがあります。Erlang ベンチマークの作成者が告白したように、
言うまでもなく、実際に何かを実行するのに十分なメモリがマシンに残っていませんでした。ストレステストアーラン
ハードウェアは何ですか?オペレーティング システムは何ですか?ベンチマーク ソース コードはどこにありますか? ベンチマークは何を測定し、証明/反証しようとしていますか?
このトピックに関する Dave Cheney のすばらしい記事は次のとおりです。
ゴルーチンの数が問題になる場合は、プログラムで簡単に制限できます: mr51m0n/gorcとこの例
を参照してください。
実行中のゴルーチンの数にしきい値を設定する
ゴルーチンを開始または停止するときにカウンターを増減できます。
実行中のゴルーチンの最小数または最大数を待機できるため、gorc
同時に実行される管理されたゴルーチンの数のしきい値を設定できます。