亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Go語言的IO庫那么多糾結該如何選擇

 更新時間:2021年06月23日 14:18:14   投稿:mrr  
在Go語言中涉及 I/O 操作的內置庫有很多種,比如: io 庫, os 庫, ioutil 庫, bufio 庫, bytes 庫, strings 庫等等。擁有這么多內置庫是好事,但是具體到涉及 I/O 的場景我們應該選擇哪個庫呢,帶著這個問題一起通過本文學習下吧

在計算機和信息技術領域里 I/O 這個術語表示輸入 / 輸出 ( 英語:Input / Output ) ,通常指數據在存儲器(內部和外部)或其他周邊設備之間的輸入和輸出,是信息處理系統與外部之間的通信。輸入是系統接收的信號或數據,輸出則是從其發(fā)送的信號或數據。

在Go語言中涉及 I/O 操作的內置庫有很多種,比如: io 庫, os 庫, ioutil 庫, bufio 庫, bytes 庫, strings 庫等等。擁有這么多內置庫是好事,但是具體到涉及 I/O 的場景我們應該選擇哪個庫呢?

io.Reader/Writer

Go語言里使用 io.Reader 和 io.Writer 兩個 interface 來抽象 I/O ,他們的定義如下。

type Reader interface {
 Read(p []byte) (n int, err error)
}

type Writer interface {
 Write(p []byte) (n int, err error)
}

io.Reader 接口代表一個可以從中讀取字節(jié)流的實體,而 io.Writer 則代表一個可以向其寫入字節(jié)流的實體。

  • io.Reader/Writer 常用的幾種實現
  • net.Conn: 表示網絡連接。
  • os.Stdin, os.Stdout, os.Stderr: 標準輸入、輸出和錯誤。
  • os.File: 網絡,標準輸入輸出,文件的流讀取。
  • strings.Reader: 字符串抽象成 io.Reader 的實現。
  • bytes.Reader: []byte抽象成 io.Reader 的實現。
  • bytes.Buffer: []byte抽象成 io.Reader 和 io.Writer 的實現。
  • bufio.Reader/Writer: 抽帶緩沖的流讀取和寫入(比如按行讀寫)。

除了這幾種實現外常用的還有 ioutil 工具庫包含了很多IO工具函數,編碼相關的內置庫 encoding/base64 、 encoding/binary 等也是通過 io.Reader 和 io.Writer 實現各自的編碼功能的。

這些常用實現和工具庫與io.Reader和io.Writer間的關系可以用下圖表示。

每種I/O庫的使用場景

io庫

io 庫屬于底層接口定義庫。它的作用主要是定義個 I/O 的基本接口和個基本常量,并解釋這些接口的功能。在實際編寫代碼做 I/O 操作時,這個庫一般只用來調用它的常量和接口定義,比如用 io.EOF 判斷是否已經讀取完,用 io.Reader 做變量的類型聲明。

// 字節(jié)流讀取完后,會返回io.EOF這個error
for {
 n, err := r.Read(buf)
 fmt.Println(n, err, buf[:n])
 if err == io.EOF {
  break
 }
}

os 庫

os 庫主要是處理操作系統操作的,它作為Go程序和操作系統交互的橋梁。創(chuàng)建文件、打開或者關閉文件、Socket等等這些操作和都是和操作系統掛鉤的,所以都通過 os 庫來執(zhí)行。這個庫經常和 ioutil , bufio 等配合使用

ioutil庫

ioutil 庫是一個有工具包,它提供了很多使用的 IO 工具函數,例如 ReadAll、ReadFile、WriteFile、ReadDir。唯一需要注意的是它們都是一次性讀取和一次性寫入,所以使用時,尤其是把數據從文件里一次性讀到內存中時需要注意文件的大小。

讀出文件中的所有內容

func readByFile() {
  data, err := ioutil.ReadFile( "./file/test.txt")
  if err != nil {
    log.Fatal("err:", err)
    return
  }
  fmt.Println("data", string(data)) 
}

將數據一次性寫入文件

func writeFile() {
  err := ioutil.WriteFile("./file/write_test.txt", []byte("hello world!"), 0644)
  if err != nil {
    panic(err)
    return
  }
}

bufio庫

bufio,可以理解為在 io 庫的基礎上額外封裝加了一個緩存層,它提供了很多按行進行讀寫的函數,從io庫的按字節(jié)讀寫變?yōu)榘葱凶x寫對寫代碼來說還是方便了不少。

func readBigFile(filePath string) error {
  f, err := os.Open(filePath)
  defer f.Close()

  if err != nil {
    log.Fatal(err)
    return err
  }

  buf := bufio.NewReader(f)
  count := 0
  // 循環(huán)中打印前100行內容
  for {
    count += 1
    line, err := buf.ReadString('\n')
    line = strings.TrimSpace(line)
    if err != nil {
      return err
    }
    fmt.Println("line", line)

    if count > 100 {
      break
    }
  }
  return nil
}

  • ReadLine和ReadString方法:buf.ReadLine(),buf.ReadString("\n")都是按行讀,只不過ReadLine讀出來的是[]byte,后者直接讀出了string,最終他們底層調用的都是ReadSlice方法。
  • bufio VS ioutil 庫:bufio VS 和 ioutil 庫都提供了讀寫文件的能力。它們之間唯一的區(qū)別是 bufio 有一個額外的緩存層。這個優(yōu)勢主要體現在讀取大文件的時候。

bytes 和 strings 庫

bytes 和 strings 庫里的 bytes.Reader 和string.Reader,它們都實現了 io.Reader 接口,也都提供了NewReader方法用來從 []byte 或者 string 類型的變量直接構建出相應的Reader實現。

r := strings.NewReader("abcde")
// 或者是 bytes.NewReader([]byte("abcde"))
buf := make([]byte, 4)
for {
 n, err := r.Read(buf)
 fmt.Println(n, err, buf[:n])
 if err == io.EOF {
  break
 }
}

另一個區(qū)別是 bytes 庫有Buffer的功能,而 strings 庫則沒有。

var buf bytes.Buffer
fmt.Fprintf(&buf, "Size: %d MB.", 85)
s := buf.String()) // s == "Size: 85 MB."

總結

關于 io.Reader 和 io.Writer 接口,可以簡單理解為讀源和寫源。也就是說,只要實現了 Reader 中的 Read 方法,這個東西就可以作為讀源,里面可以包含數據,被我們讀取。 Writer 也是如此。

以上是我對Go語言里做 I/O 操作時經常會用到的Go語言內置庫在使用場景和每個庫要解決的問題上的一些總結,希望能幫大家理清思路,作為參考,在開發(fā)任務中需要時正確選擇合適的庫完成 I/O 操作。如果文章中的敘述有錯誤,歡迎留言指正,也歡迎在留言中對文章內容進行探討和提出建議。

以上就是Go語言的IO庫那么多糾結該如何選擇的詳細內容,更多關于Go語言IO庫的資料請關注腳本之家其它相關文章!

相關文章

  • Go語言讀取YAML 配置文件的兩種方式分享

    Go語言讀取YAML 配置文件的兩種方式分享

    在日常開發(fā)中,YAML 格式的文件基本上被默認為是配置文件,其內容因為縮進帶來的層級感看起來非常直觀和整潔。本文分享了讀取YAML 配置文件的兩種方式,需要的可以參考一下
    2022-12-12
  • Go語言清除文件中空行的方法

    Go語言清除文件中空行的方法

    這篇文章主要介紹了Go語言清除文件中空行的方法,實例分析了Go語言針對文件的操作技巧,具有一定參考借鑒價值,需要的朋友可以參考下
    2015-02-02
  • golang的協程上下文的具體使用

    golang的協程上下文的具體使用

    golang的context?主要用來在?goroutine?之間傳遞上下文信息,包括:取消信號、超時時間、截止時間、k-v?等,本文就詳細的來介紹一下golang的協程上下文的具體使用,感興趣的可以了解一下
    2022-04-04
  • 幾個小技巧幫你實現Golang永久阻塞

    幾個小技巧幫你實現Golang永久阻塞

    Go 的運行時的當前設計,假定程序員自己負責檢測何時終止一個 goroutine 以及何時終止該程序。有時候我們需要的是使程序阻塞在這一行,本文就來詳細的介紹一下,感興趣的可以了解一下
    2021-12-12
  • golang實現ip訪問限制及提交次數

    golang實現ip訪問限制及提交次數

    在?Web?應用中,通常會需要對?IP?訪問進行限制以及控制提交次數,本文將使用中間件或者基于?Redis?這樣的緩存服務來實現,感興趣的可以了解下
    2024-10-10
  • Golang中下劃線(_)的不錯用法分享

    Golang中下劃線(_)的不錯用法分享

    golang中的下劃線表示忽略變量的意思,也沒有產生新的變量,但是后面的表達式依然會被執(zhí)行,本文為大家整理了golang中下劃線的一些不錯的用法,需要的可以參考下
    2023-05-05
  • golang多維度排序及題解最長連續(xù)序列

    golang多維度排序及題解最長連續(xù)序列

    這篇文章主要為大家介紹了golang多維度排序及題解最長連續(xù)序列示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-10-10
  • Golang 實現 Redis系列(六)如何實現 pipeline 模式的 redis 客戶端

    Golang 實現 Redis系列(六)如何實現 pipeline 模式的 redis 客戶端

    pipeline 模式的 redis 客戶端需要有兩個后臺協程負責 tcp 通信,調用方通過 channel 向后臺協程發(fā)送指令,并阻塞等待直到收到響應,本文是使用 golang 實現 redis 系列的第六篇, 將介紹如何實現一個 Pipeline 模式的 Redis 客戶端。
    2021-07-07
  • Go語言sync包與鎖實現限制線程對變量的訪問

    Go語言sync包與鎖實現限制線程對變量的訪問

    本文主要介紹了Go語言sync包與鎖實現限制線程對變量的訪問,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2023-04-04
  • 在 Golang 中實現 Cache::remember 方法詳解

    在 Golang 中實現 Cache::remember 方法詳解

    這篇文章主要介紹了在 Golang 中實現 Cache::remember 方法詳解,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-03-03

最新評論