douji8549 2017-08-01 17:20
浏览 16
已采纳

常规表现

I have started to learn Go, it's fun and easy. But working with goroutines I have seen little benefit in performance.

If I try to sequentially add 1 million numbers two times in 2 functions:

package main

import (
    "fmt"
    "time"
)

var sumA int
var sumB int

func fSumA() {
    for i := 0; i < 1000000; i++ {
        sumA += i
    }
}

func fSumB() {
    for i := 0; i < 1000000; i++ {
        sumB += i
    }
}

func main() {
    start := time.Now()
    fSumA()
    fSumB()
    sum := sumA + sumB
    fmt.Println("Elapsed time", time.Since(start))
    fmt.Println("Sum", sum)
}

It takes 5 ms.

MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.724406ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.358165ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.042528ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.469628ms
Suma total 999999000000

When I try to do the same thing with 2 goroutines:

package main

import (
    "fmt"
    "sync"
    "time"
)

var wg sync.WaitGroup

var sumA int
var sumB int

func fSumA() {
    for i := 0; i < 1000000; i++ {
        sumA += i
    }
    wg.Done()
}

func fSumB() {
    for i := 0; i < 1000000; i++ {
        sumB += i
    }
    wg.Done()
}

func main() {
    start := time.Now()
    wg.Add(2)
    go fSumA()
    go fSumB()
    wg.Wait()
    sum := sumA + sumB
    fmt.Println("Elapsed time", time.Since(start))
    fmt.Println("Sum", sum)
}

I get more or less the same result, 5 ms. My computer is a MacBook pro (Core 2 Duo). I don't see any performance improvement. Maybe is the processor?

MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.258415ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.528498ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.273565ms
Suma total 999999000000
MacBook-Pro-de-Pedro:hello pedro$ ./bin/hello
Elapsed time 5.539224ms
Suma total 999999000000
  • 写回答

1条回答 默认 最新

  • douduxia1551 2017-08-01 19:32
    关注

    Here how you can test this with the golangs own benchmark tool:

    Create a test go file (e.g. main_test.go).

    Note: _test.go has to be the file ending!

    Copy the following code there or create your own Benchmarks:

    package main
    
    import (
        "sync"
        "testing"
    )
    
    var GlobalInt int
    
    func BenchmarkCount(b *testing.B) {
        var a, c int
        count(&a, b.N)
        count(&c, b.N)
        GlobalInt = a + c // make sure the result is actually used
    }
    
    func count(a *int, max int) {
        for i := 0; i < max; i++ {
            *a += i
        }
    }
    
    var wg sync.WaitGroup
    
    func BenchmarkCountConcurrent(b *testing.B) {
        var a, c int
        wg.Add(2)
        go countCon(&a, b.N)
        go countCon(&c, b.N)
        wg.Wait()
    
        GlobalInt = a + c // make sure the result is actually used
    }
    
    func countCon(a *int, max int) {
        for i := 0; i < max; i++ {
            *a += i
        }
        wg.Done()
    }
    

    Run with:

    go test -bench .
    

    Result on my Mac:

    $ go test -bench .
    BenchmarkCount-8                500000000            3.50 ns/op
    BenchmarkCountConcurrent-8      2000000000           1.98 ns/op
    PASS
    ok      MyPath/MyPackage        6.309s
    

    Most important value is the time/op. The smaller the better. Here 3.5 ns/op for normal counting, 1.98 ns/op for concurrent counting.

    EDIT: Here you can read up on golang Testing and Benchmark.

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 oracle集群安装出bug
  • ¥15 关于#python#的问题:自动化测试
  • ¥20 问题请教!vue项目关于Nginx配置nonce安全策略的问题
  • ¥15 教务系统账号被盗号如何追溯设备
  • ¥20 delta降尺度方法,未来数据怎么降尺度
  • ¥15 c# 使用NPOI快速将datatable数据导入excel中指定sheet,要求快速高效
  • ¥15 再不同版本的系统上,TCP传输速度不一致
  • ¥15 高德地图点聚合中Marker的位置无法实时更新
  • ¥15 DIFY API Endpoint 问题。
  • ¥20 sub地址DHCP问题