精品欧美一区二区三区在线观看 _久久久久国色av免费观看性色_国产精品久久在线观看_亚洲第一综合网站_91精品又粗又猛又爽_小泽玛利亚一区二区免费_91亚洲精品国偷拍自产在线观看 _久久精品视频在线播放_美女精品久久久_欧美日韩国产成人在线

Go 中如何高效遍歷目錄?探索幾種方法

開發 前端
在本文中,我們系統介紹了 Go 中多種遍歷目錄文件的方法。從傳統的 ioutil.ReadDir?,到 Go 1.16 引入的 os.ReadDir,os.File? 的 ReadDir? 方法。

目錄遍歷是一個很常見的操作,它的使用場景有如文件目錄查看(最典型的應用如 ls 命令)、文件系統清理、日志分析、項目構建等。

本文將嘗試逐步介紹在 Go 中幾種遍歷目錄文件的方法,從傳統的 ioutil.ReadDir 函數開始,逐漸深入。

圖片圖片

文中也會提供示例代碼、提供一些性能剖析,以便于大家更好地理解。

ioutil.ReadDir

首先,Go 中目錄文件遍歷的第一種方式是 ioutil.ReadDir 函數。

在 Go 1.16 版本前,ioutil.ReadDir 就是遍歷目錄的標準方法,它的返回結構是目錄中文件的 FileInfo 列表,簡單直接。

示例代碼:

func main() {
    files, err := ioutil.ReadDir(".")
    if err != nil {
        log.Fatal(err)
    }

    for _, f := range files {
        fmt.Println(f.Name())
    }
}

但它的缺點也非常明顯,性能不高。導致它的主要原因有如下幾點:

完全加載

這就導致了 ioutil.ReadDir 在返回結果前,會將目錄下所有文件的信息完全加載到內存中。對于包含大量文件的目錄,它就需要在內存中存儲大量的 FileInfo 對象,毫無疑問,這會增加內存使用。

FileInfo 開銷

由于是完全加載,每個 FileInfo 對象都包含了文件的詳細信息,如文件名、大小、修改時間等都會在返回之前都已經加載完成。但獲取這些信息需進行系統調用。而每個文件都要做這樣的調用,當文件數量很多時,這些系統調用的累積開銷可以變得不容忽視了。

無法分批處理

由于 ioutil.ReadDir 是一次性返回所有文件信息,沒有提供分批處理的能力。無論目錄中有多少文件,都要等待所有文件信息讀取完成,這在處理目錄中包含大量文件的場景中,也就無法提前并行處理,效率是可想而知的。

這一點其實和我們前面的一篇文章,介紹的 GO 中按行(或者說按塊)讀取文件的邏輯是類似的,一次加載全部內容,有潛在的性能問題。

由于 ioutil.ReadDir 有這么多的缺點,所以它在 Go 1.16 及更高版本已經被棄用了。

那現在我們該用什么方法呢?

os.ReadDir

從 Go 1.16 版本起,標準庫針對目錄遍歷查看提供了新的函數 os.ReadDir,以用來簡化和提高遍歷目錄文件的效率。

函數簽名如下:

func ReadDir(name string) ([]DirEntry, error)

os.ReadDir 函數返回一個按文件名排序的 DirEntry 類型切片。如果在讀取目錄項時遇到錯誤,它也會盡量返回已讀取內容。這種設計同時兼顧了效率和錯誤處理的需要。

示例代碼:

func main() {
    files, err := os.ReadDir(".")
    if err != nil {
        log.Fatal(err)
    }

    for _, file := range files {
        fmt.Println(file.Name())
    }
}

os.ReadDir 相比于舊方法 ioutil.ReadDir 的有什么優勢?為什么丟棄 ioutil.ReadDir 而引入這個新的 os.ReadDir。

如果對比兩者源碼,會發現差異主要在返回的類型上。os.ReadDir 返回的 []DirEntry 而非 []FileInfo。它還具有性能優勢。

為什么?

因為 DirEntry 允許按需獲取文件詳情,即懶加載,而非是遍歷目錄時立即加載所有文件屬性。很多場景下,我們并不需要

我在 MacOS 系統下測試的 DirEntry 接口的實際變量類型為 os.unixDirent。

它的源碼如下:

func (d *unixDirent) Name() string   { return d.name }
func (d *unixDirent) IsDir() bool    { return d.typ.IsDir() }
func (d *unixDirent) Type() FileMode { return d.typ }

func (d *unixDirent) Info() (FileInfo, error) {
    if d.info != nil {
        return d.info, nil
    }
    return lstat(d.parent + "/" + d.name)
}

我們只有在調用 Info 方法時,才會真正通過 lstat 發起系統調用。

如果你有將舊代碼遷移到 DirEntry 的需求, Go 1.17 還引入了 fs.FileInfoToDirEntry 函數,允許我們將 FileInfo 對象轉換為 DirEntry 對象。

info, _ := os.Stat("somefile")dirEntry := fs.FileInfoToDirEntry(info)

看到這,對于認真思考的朋友,或許已經發現我們還有一個問題沒解決,即 os.ReadDir 不是也不支持分批處理的能力嗎?

繼續往下看吧,我將介紹一個更底層的方法。

os.File 的 ReadDir 方法

我們知道 os.Open 是用于打開文件的,但其實它也可用于打開目錄。如果 os.Open 打開的是目錄,我們在它返回的 os.File 上調用 ReadDir 以查看目錄內容。

示例代碼:

func main() {
    dir, err := os.Open(".")
    if err != nil {
        log.Fatal(err)
    }
    defer dir.Close()

    files, err := dir.ReadDir(-1)
    if err != nil {
        log.Fatal(err)
    }

    for _, file := range files {
        fmt.Println(file.Name())
    }
}

如上的代碼其實類似于 os.ReadDir 內容的實現代碼。

os.ReadDir 源碼如下:

func ReadDir(name string) ([]DirEntry, error) {
    f, err := Open(name)
    if err != nil {
        return nil, err
    }
    defer f.Close()

    dirs, err := f.ReadDir(-1)
    sort.Slice(dirs, func(i, j int) bool { return dirs[i].Name() < dirs[j].Name() })
    return dirs, err
}

這種方法更底層,提供了更多的靈活性。我們就可以用它分批讀取目標。

如何實現呢?

核心就是那句的 dir.ReadDir(-1),它的入參指定了每次讀取文件的數量,而 -1 表示讀取目錄的所有內容。我們只要將 -1 改為分批讀取的數量即可,多次循環即可。

示例代碼:

func main() {
    dir, err := os.Open(".")
    if err != nil {
        log.Fatal(err)
    }
    defer dir.Close()

    for {
        files, err := dir.ReadDir(10) // 每批讀取10個條目
        if err == io.EOF {
            break // 遍歷完成
        }
        if err != nil {
            log.Fatal(err) // 處理其他錯誤
        }

        for _, file := range files {
            fmt.Println(file.Name())
        }
    }
}

這段代碼演示了如何使用 File.ReadDir 分批處理目錄中的文件。通過這種方式,可以更有效地管理內存使用。

補充一點

在寫這篇文章時,我發現 os.File 有兩個查看目錄的方法,分別是 Readdir 和 ReadDir。功能上的區別是新的 ReadDir 返回的是 []DirEntry,而 Readdir 返回的是 []FileInfo。

換句話說,ReadDir 本質上是 Readdir 的升級版。

它們的函數簽名,如下所示:

func (f *File) Readdir(n int) ([]FileInfo, error)
func (f *File) ReadDir(n int) ([]DirEntry, error)

這算是不支持可選參數和重載,但要解決兼容問題采取的措施嗎?真的是蚌埠住了。

目錄的遞歸遍歷

現在,還差最后一個內容沒有介紹,那就是遞歸目錄遍歷。

針對目錄的遞歸遍歷,Go 中提供了一個專門的函數,filepath.Walk。它可以遍歷指定目錄下的所有子目錄。

示例代碼:

func main() {
    err := filepath.Walk(".", func(path string, info os.FileInfo, err error) error {
        if err != nil {
            return err
        }
        fmt.Println(path)
        return nil
    })
    if err != nil {
        fmt.Printf("error walking the path %v: %v\n", ".", err)
    }
}

我們通過遍歷的回調函數中在處理每個文件。它簡化了目錄的遞歸遍歷,但對于大型或深層次的目錄結構,同樣存在著提前加載 FileInfo 的問題。

針對這個問題,在 Go1.16 版本也引入了基于 DirEntry 版的 filepath.WalkDir 函數。

filepath.WalkDir 的函數簽名如下:

func WalkDir(root string, fn fs.WalkDirFunc) error

fs.WalkDirFunc 的定義如下:

type WalkDirFunc func(path string, d DirEntry, err error) error

新函數的遍歷回調參數是 DirEntry,而非 FileInfo。現在,filepath.WalkDir 也有了延遲加載 FileInfo 的能力了。

現在,我們再來看下這張圖。

圖片圖片

總結

在本文中,我們系統介紹了 Go 中多種遍歷目錄文件的方法。從傳統的 ioutil.ReadDir,到 Go 1.16 引入的 os.ReadDir,os.File 的 ReadDir 方法。每種方法適用于不同的場景,如何選擇要取決于你的需求、Go 版本、性能。如果你需要遞歸遍歷,也可以使用基于 DirEntry 的 filepath.WalkDir 實現,提高遍歷的性能。

引用鏈接

[1] Go 中如何遍歷目錄?探索幾種方法: https://www.poloxue.com/2024-02-22-list-directory-in-golang/

責任編輯:武曉燕 來源: 碼途漫漫
相關推薦

2021-03-08 09:32:04

Python文件命令

2018-08-09 20:47:41

2021-06-08 11:42:12

Pandas數據分析Python

2009-08-25 09:22:01

DataGridVie

2024-06-03 08:26:34

Android開發監聽器

2020-10-16 18:35:53

JavaScript字符串正則表達式

2009-09-18 12:29:55

2010-05-17 15:17:06

MySQL常用操作

2013-08-21 11:31:21

iPhone圖片方法

2010-06-03 08:55:43

LINQ

2024-10-07 09:03:15

2010-04-30 16:22:07

Unix終端

2010-01-22 14:46:25

C++語言

2010-10-26 09:23:03

Web Service

2013-02-25 14:46:49

2011-06-16 10:48:33

session

2020-08-24 08:05:47

JavaScriptJavaScript 頁面

2021-02-26 13:20:48

Shell空行Linux

2009-09-09 11:24:46

PHP實現MVC

2020-01-10 16:23:44

Springboot停止服務Java
點贊
收藏

51CTO技術棧公眾號

日本精品视频一区二区| 99精品视频一区| 久久久久久国产三级电影| 快播日韩欧美| 亚洲天堂视频网站| 日韩电影在线视频| 精品精品欲导航| 国产极品美女高潮无套久久久| av资源在线观看免费高清| 国产自产v一区二区三区c| 久久久噜噜噜久久中文字免| 亚洲一二三四视频| 第四色中文综合网| 在线一区二区三区| 国产91在线亚洲| 国产福利片在线| 国产福利一区二区三区| 日本中文字幕不卡免费| 欧美成人精品欧美一| 台湾色综合娱乐中文网| 3751色影院一区二区三区| 欧美变态另类刺激| www免费视频观看在线| 91啦中文在线观看| 国产99午夜精品一区二区三区| 香蕉污视频在线观看| 激情综合在线| 久久久精品视频在线观看| 男女黄床上色视频| 综合激情网...| 91.麻豆视频| 无码无遮挡又大又爽又黄的视频| 久草在线视频福利| 亚洲私人黄色宅男| 亚洲日本无吗高清不卡| 欧美视频综合| 97国产一区二区| 国产精品久久久久久久久久久久冷| 在线免费看av的网站| 久久精品卡一| 欧美亚州一区二区三区| 国产中文字幕免费| 亚洲第一天堂| 久久精品99久久久香蕉| 中文天堂资源在线| 国产一区2区| 欧美精品一区二区三区四区| 亚洲av综合色区无码另类小说| 欧美一区=区三区| 欧洲人成人精品| av动漫在线观看| 爱搞国产精品| 欧美性生交大片免费| 91九色丨porny丨国产jk| 欧美高清另类hdvideosexjaⅴ| 1区2区3区国产精品| 亚洲欧洲一区二区在线观看| 国产中文字幕在线播放| 欧美韩日一区二区三区四区| 日本在线观看一区二区| 二区三区在线| 国产精品看片你懂得| 亚洲一区尤物| 黄色一级大片在线免费看产| √…a在线天堂一区| 国产精品99久久久久久大便| 二区在线播放| 亚洲一区电影777| 日韩国产欧美亚洲| 亚洲黄色网址| 在线观看国产精品网站| jizzzz日本| 激情不卡一区二区三区视频在线| 日韩一区二区在线观看视频播放| 香蕉视频免费网站| 日韩影视高清在线观看| 亚洲欧美中文字幕在线一区| 国产精品情侣呻吟对白视频| 91精品二区| 国内精品小视频| 一级黄色免费网站| 捆绑紧缚一区二区三区视频| 99国精产品一二二线| 神马午夜精品95| 国产日韩亚洲欧美综合| 一级一片免费播放| 免费在线国产视频| 一本到不卡免费一区二区| 91制片厂毛片| 精品五月天堂| 在线国产精品播放| 久草国产在线观看| 秋霞成人午夜伦在线观看| 5566av亚洲| 免费一级在线观看播放网址| 中文字幕一区二区视频| 日韩xxxx视频| 亚洲国产尤物| 亚洲成人999| 欧美亚洲色综久久精品国产| 禁久久精品乱码| 国产精品久久久久久久久久久不卡 | 亚洲va在线va天堂va偷拍| 亚洲一区二区三区中文字幕在线观看 | 黄色永久免费网站| 99亚洲乱人伦aⅴ精品| 国产午夜精品全部视频播放 | 午夜天堂精品久久久久| 日韩av免费看网站| 国产富婆一级全黄大片| 久久婷婷国产综合精品青草| 黄色录像特级片| 浪潮色综合久久天堂| 精品美女一区二区| 香蕉成人在线视频| 亚洲欧美日韩在线观看a三区| 91免费视频网站| 国产在线电影| 精品国产乱码久久久久久天美| 欧美激情第一区| 欧美视频免费| 欧美影院久久久| 亚洲免费成人在线| 日韩毛片高清在线播放| 情侣黄网站免费看| 久久动漫网址| 久久久免费观看视频| 亚洲大尺度在线观看| fc2成人免费人成在线观看播放| 波多野结衣激情| 日本中文字幕一区二区| 国产视频精品在线| 国产亚洲第一页| 国产在线一区二区综合免费视频| 日韩精品大片| 伊人网在线播放| 亚洲国产精品一区二区三区| 精品一区二区三区四| 国产成人h网站| 黄色www在线观看| 日韩成人一区| 亚洲新声在线观看| 亚洲av无码精品一区二区| 91麻豆福利精品推荐| 黄www在线观看| 欧美三级电影在线| 欧美亚洲第一页| 日韩porn| 色婷婷久久99综合精品jk白丝| 一本色道久久综合亚洲精品图片| 国产伦理一区| 欧洲一区二区在线观看| 婷婷午夜社区一区| 国产亚洲欧美另类中文| 久久人人爽人人爽人人片av免费| 久久久91精品国产一区二区精品| 国产日韩一区二区在线观看| 欧美三级三级| 国产精品女人网站| 色网站免费在线观看| 91精品国产免费| 激情综合五月网| 成人蜜臀av电影| 欧美韩国日本在线| 国产一区二区亚洲| 成人福利在线观看| 丁香高清在线观看完整电影视频| 精品成人一区二区| 国产性猛交╳xxx乱大交| 久久久久国产精品免费免费搜索| 另类小说色综合| 97视频精品| 春色成人在线视频| 成人福利av| 久久精品国产视频| 欧美一级淫片免费视频魅影视频| 欧美午夜女人视频在线| 中文字幕精品国产| 在线能看的av| 国产精品久久一卡二卡| 久久黄色一级视频| 先锋影音久久久| 亚洲精品在线免费| 亚洲精品福利| 日本一区二区三区四区视频| 日本高清视频在线播放| 欧美精品一区二区三区很污很色的 | 色又黄又爽网站www久久| 国产第一页精品| 国产91精品一区二区麻豆亚洲| 凹凸国产熟女精品视频| 国产精品国产一区| 久久久久欧美| 国产精品白丝久久av网站| 欧美一级大片视频| 麻豆影视国产在线观看| 亚洲精品二三区| 国产精品国产一区二区三区四区| 激情成人中文字幕| 亚洲天堂av中文字幕| 成人性色生活片免费看爆迷你毛片| 国产裸体舞一区二区三区| 欧美日韩亚洲一区二区三区在线| 欧美极品jizzhd欧美| 日韩区欧美区| 国产精品一区二区久久精品| 在线男人天堂| 九色成人免费视频| 北岛玲一区二区三区| 日韩av综合中文字幕| av网站在线观看免费| 欧美性生交xxxxxdddd| 久久久久久久蜜桃| 国产精品三级电影| 久久精品视频18| 波多野结衣中文一区| 欧美性猛交xx| 激情av综合网| 国产成人综合一区| 伊人天天综合| 久久这里只有精品8| 婷婷丁香综合| 婷婷五月色综合| 曰本一区二区三区视频| 国内不卡一区二区三区| 最新精品在线| www 成人av com| 高清不卡一区| 成人在线视频福利| 成人免费视频观看| 国产精品人人做人人爽| 国产精品高清乱码在线观看| 欧美与黑人午夜性猛交久久久| 激情av在线| 欧美大秀在线观看| 欧美卡一卡二| 高清欧美性猛交xxxx黑人猛交| 在线电影福利片| 欧美日本精品在线| 少妇av在线| 欧美激情精品久久久久久久变态| 9191在线播放| 欧美国产一区二区三区| 密臀av在线| 国内精品模特av私拍在线观看| a级片在线免费| 97视频在线观看亚洲| 小草在线视频免费播放| 热草久综合在线| 日本高清不卡一区二区三区视频| 欧美最猛性xxxxx亚洲精品| 一级毛片久久久| 国产精品扒开腿做| 粉嫩91精品久久久久久久99蜜桃| 国产精品普通话| www.久久草.com| 99在线视频播放| 久久精品亚洲成在人线av网址| 国产精品一区二区a| 欧美高清视频看片在线观看| 蜜桃精品久久久久久久免费影院| 国产一区二区三区91| 色综合久久久久久久久五月| 99re6这里只有精品| 亚洲啊啊啊啊啊| 亚洲青涩在线| 日韩无套无码精品| 激情小说亚洲一区| 免费黄色av网址| 91麻豆免费在线观看| 亚洲av成人无码久久精品 | 日韩国产欧美精品一区二区三区| 日本一区高清| 日韩亚洲欧美成人| 久久www人成免费看片中文| 欧美综合一区第一页| 欧美一区=区三区| 国产精品白丝jk白祙| 日韩激情网站| 一区二区三区精品国产| 精品成人久久| 国产三级三级三级看三级| 韩国欧美国产一区| 日韩av一二区| 亚洲啪啪综合av一区二区三区| 亚洲天堂日韩av| 91麻豆精品国产91久久久使用方法| 丰满人妻一区二区| 亚洲最新中文字幕| heyzo高清在线| 国产美女久久久| 加勒比中文字幕精品| 亚洲欧美日韩国产yyy| 在线成人国产| 日韩在线一区视频| 久久综合久久鬼色中文字| 国产成人自拍网站| 日本韩国一区二区| 国 产 黄 色 大 片| 日韩在线视频免费观看高清中文| 国产盗摄一区二区| 国产日韩欧美在线| 秋霞在线一区| 91亚洲精品国产| 国内精品写真在线观看| 99久久久无码国产精品性| 尤物视频一区二区| 亚洲一区二区三区高清视频| 亚洲男人天堂古典| 日本aa在线| 91久久综合亚洲鲁鲁五月天| 自拍亚洲一区| 日韩欧美国产综合在线| 国产精品一二三区| 日本精品久久久久中文| 午夜久久久久久| 国产成人三级在线播放| 中文字幕亚洲欧美在线 | 亚洲高清电影| 中文字幕avav| 国产精品夫妻自拍| 99re热视频| 亚洲精品视频免费| av资源新版天堂在线| 97超级碰碰| 婷婷综合五月| 色婷婷.com| 国产精品私人影院| 五月婷婷六月婷婷| 亚洲欧美精品中文字幕在线| 伊人成综合网站| 久久久一本精品99久久精品| 一本久道久久综合狠狠爱| 国产女主播在线播放| 一区二区三区免费看视频| jlzzjlzz亚洲女人18| 美女av一区二区三区| 精品国产乱码一区二区三区 | 国精产品一区| 成人网欧美在线视频| **女人18毛片一区二区| 极品粉嫩美女露脸啪啪| 亚洲欧美综合另类在线卡通| 亚洲自拍偷拍另类| 日韩有码在线视频| 国产精品白丝久久av网站| 肉大捧一出免费观看网站在线播放| 国产在线播放一区三区四| 搜索黄色一级片| 日韩一区二区三区电影| 婷婷在线播放| 国语精品中文字幕| 久久国产成人| 国内精品卡一卡二卡三| 欧美男男青年gay1069videost| 亚洲天天影视| 97中文在线| av成人激情| 日韩视频在线观看免费视频| 欧美日韩www| 日本一本在线免费福利| 久久精品国产精品青草色艺| 久久久精品五月天| 99热6这里只有精品| 欧美xxxxx牲另类人与| 老色鬼在线视频| 亚洲国产综合自拍| 国产丶欧美丶日本不卡视频| 久久久久亚洲av成人毛片韩| 亚洲一区二区久久| 免费精品一区二区三区在线观看| 和岳每晚弄的高潮嗷嗷叫视频| 久久久高清一区二区三区| 国产精品高潮呻吟av| 性欧美暴力猛交69hd| 欧美在线色图| 国产chinesehd精品露脸| 欧美视频免费在线| 在线看黄色av| 国产视频一区二区不卡| 丝袜诱惑亚洲看片| 欧美精品xxxxx| 亚洲天堂男人天堂| 一本一道久久a久久| 国产自偷自偷免费一区| 一区二区三区在线看| 国产一区二区三区福利| 91日韩久久| 日韩av在线免费观看不卡| 欧美三级日本三级| 亚洲天堂成人在线视频| 欧美影院在线| www.99av.com| 亚洲国产精品久久久久秋霞影院| 国产视频网址在线| 国产精品久久久久久久久久直播 | 在线免费观看一区| 黄色在线观看视频网站| 在线不卡视频一区二区| 久久久综合激的五月天|