试了下 Go ,不用协程要 6130ms 左右,用了协程跟 Java 差不多,1110ms 左右:
```go
package main
import (
"fmt"
"math/rand"
"sync"
"time"
)
const (
tosses = 10_000 // 1e4
iterations = 100_000 // 1e5
)
func main() {
start := time.Now()
// streakMap := make(map[int]int64) // 6130±20
streakMap := sync.Map{} // 1110±20
var wg sync.WaitGroup
for i := 0; i < iterations; i++ {
wg.Add(1)
go func() {
defer wg.Done()
max := maxStreak()
//streakMap[max] = streakMap[max] + 1
m, _ := streakMap.Load(max)
if m == nil {
m = int64(0)
}
streakMap.Store(max, m.(int64)+1)
}()
}
wg.Wait()
var total int64
//for _, value := range streakMap {
// total += value
//}
streakMap.Range(func(key, value any) bool {
if value == nil {
value = int64(0)
}
total += value.(int64)
return true
})
//for key, value := range streakMap {
// fmt.Printf("Max: %d, count: %d, percent: %.2f%%\n", key, value, (float64(value)*100)/float64(total))
//}
streakMap.Range(func(key, value any) bool {
fmt.Printf("Max: %d, count: %d, percent: %.2f%%\n", key, value, (float64(value.(int64))*100)/float64(total))
return true
})
// print execute time in ms
fmt.Printf("Execution time: %dms\n", time.Since(start).Milliseconds())
}
func maxStreak() (max int) {
var streak int
var r = rand.New(rand.NewSource(time.Now().UnixNano()))
for i := 0; i < tosses; i++ {
current := r.Intn(2) == 1
if current {
streak++
} else {
streak = 0
}
if streak > max {
max = streak
}
}
return max
}
```