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

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

在 GOLANG 中盡可能快地遞歸遍歷所有文件夾中的所有文件

在 GOLANG 中盡可能快地遞歸遍歷所有文件夾中的所有文件

Go
肥皂起泡泡 2022-11-28 10:44:11
我面臨一個問題,即使在論壇上花了一天時間,我仍然無法完全理解和解決。所以在這里,我做了一個循環所有文件夾及其子文件夾的函數,它有 2 個子函數:- 對于找到的每個文件,列出文件的名稱。- 對于找到的每個文件夾,重新啟動相同的父函數以再次查找子文件和文件夾。為簡化起見,該宏以遞歸方式列出了樹中的所有文件。但我的目標是盡可能快地完成,所以每次遇到新文件夾時我都會運行一個新的 goroutine。問題:我的問題是,當樹結構太大(文件夾和子文件夾中的文件夾太多......)時,腳本會生成太多線程,因此會出現錯誤。所以我增加了這個限制,但突然間它不再需要電腦了:/所以我的問題是,如何制作適合我的代碼的工作系統(帶池大?。??不管我怎么看,我都沒有看到如何說,例如,生成新的 goroutines 達到一定的限制,清空緩沖區的時間。源代碼:https ://github.com/LaM0uette/FilesDIR/tree/V0.5主要的:package mainimport (    "FilesDIR/globals"    "FilesDIR/task"    "fmt"    "log"    "runtime/debug"    "sync"    "time")func main() {    timeStart := time.Now()    debug.SetMaxThreads(5 * 1000)    var wg sync.WaitGroup    // task.DrawStart()    /*        err := task.LoopDir(globals.SrcPath)        if err != nil {            log.Print(err.Error())        }    */    err := task.LoopDirsFiles(globals.SrcPath, &wg) // globals.SrcPath = My path with ~2000000 files ( this is a serveur of my entreprise)    if err != nil {        log.Print(err.Error())    }    wg.Wait()    fmt.Println("FINI: Nb Fichiers: ", task.Id)    timeEnd := time.Since(timeStart)    fmt.Println(timeEnd)}
查看完整描述

1 回答

?
撒科打諢

TA貢獻1934條經驗 獲得超2個贊

如果您不想使用任何外部包,您可以創建一個單獨的工作程序來處理文件,然后啟動任意數量的工作程序。之后,在你的主線程中遞歸地進入樹,并將工作發送給工人。如果任何工人“有時間”,它將從工作頻道中挑選以下工作并進行處理。


var (

    wg   *sync.WaitGroup

    jobs chan string = make(chan string)

)


func loopFilesWorker() error {

    for path := range jobs {

        files, err := ioutil.ReadDir(path)

        if err != nil {

            wg.Done()

            return err

        }


        for _, file := range files {

            if !file.IsDir() {

                fmt.Println(file.Name())

            }

        }

        wg.Done()

    }

    return nil

}


func LoopDirsFiles(path string) error {

    files, err := ioutil.ReadDir(path)

    if err != nil {

        return err

    }

    //Add this path as a job to the workers

    //You must call it in a go routine, since if every worker is busy, then you have to wait for the channel to be free.

    go func() {

        wg.Add(1)

        jobs <- path

    }()

    for _, file := range files {

        if file.IsDir() {

            //Recursively go further in the tree

            LoopDirsFiles(filepath.Join(path, file.Name()))

        }

    }

    return nil

}


func main() {

    //Start as many workers you want, now 10 workers

    for w := 1; w <= 10; w++ {

        go loopFilesWorker()

    }

    //Start the recursion

    LoopDirsFiles(globals.SrcPath)

    wg.Wait()

}


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

添加回答

舉報

0/150
提交
取消
微信客服

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

幫助反饋 APP下載

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

公眾號

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