亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

Golang WaitGroup 導致內存泄漏,我該怎么做才能改進這個功能

Golang WaitGroup 導致內存泄漏,我該怎么做才能改進這個功能

Go
aluckdog 2021-11-01 10:53:19
我一直在努力尋找我們應用程序中的內存泄漏,并且一直在使用 pprof 工具來了解發生了什么。當我查看堆時,我不斷看到以下函數,但我不明白為什么(或是否)它實際上是一個問題。func CreateClients(raw []byte) bool {    macs := []string{}    conn := FormatConn(raw)    if conn.Ap_Mac != "" {        var wg sync.WaitGroup        var array []Client        c1 := make(chan Client)        clients := FormatClients(conn)        wg.Add(len(clients))        for _, c := range clients {            go func(d Client) {                defer wg.Done()                c1 <- UpdateClients(d)            }(c)        }        go func() {            defer wg.Done()            for {                select {                case client := <-c1:                    array = append(array, client)                    macs = append(macs, client.Client_Mac)                }            }        }()        wg.Wait()        // Do some other stuff    ...}UpdateClients 函數更新 Mongo 中的客戶端模型。當它返回時,我需要每個客戶端 - 所以我可以用 ES 索引它,另外我需要一個 mac 數組來做一些其他的事情。我已經瀏覽了在線示例,并認為這是循環通道的推薦方式。我的 pprof 堆看起來像這樣,并且在幾天內穩定增長:7.53MB of 9.53MB total (79.00%)Dropped 234 nodes (cum <= 0.05MB)Showing top 5 nodes out of 28 (cum >= 1MB)      flat  flat%   sum%        cum   cum%       2MB 21.00% 21.00%        2MB 21.00%  strings.Replace    1.51MB 15.89% 36.89%     1.51MB 15.89%  github.com/PolkaSpots/worker/worker.func·006    1.51MB 15.87% 52.76%     1.51MB 15.87%  github.com/PolkaSpots/worker/worker.func·008    1.50MB 15.75% 68.51%     1.50MB 15.75%  newproc_m       1MB 10.50% 79.00%        1MB 10.50%  gopkg.in/mgo.v2/bson.(*decoder).readStr有沒有更有效/推薦的方法來實現這一目標?
查看完整描述

1 回答

?
郎朗坤

TA貢獻1921條經驗 獲得超9個贊

接收循環永不中斷:


  for {

            select {

            case client := <-c1:

            ...

   }

它沒有停止條件,沒有超時,什么都沒有——所以它會永遠掛在那里——即使你的整個函數退出。它會同時泄漏 goroutine 和通道。


最重要的是,wg.Done當這個循環退出時,你會推遲 a ,但你沒有做wg.Add匹配它。所以如果這個循環退出,你會恐慌。


您需要做的是找到某種方法來停止 for/select 循環。最簡單的方法 IMO - 在 之后添加第二個接收數據的通道wg.Wait(),但不要wg.Done()在該 goroutine 中執行。


查看完整回答
反對 回復 2021-11-01
  • 1 回答
  • 0 關注
  • 212 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號