首頁  >  文章  >  後端開發  >  如何在 Go 中建立“tail -f”等效項?

如何在 Go 中建立“tail -f”等效項?

DDD
DDD原創
2024-10-30 03:33:02560瀏覽

How to Create a

Go 中類似「tail -f」的產生器

任務是建立一個類似Python 的「tail -f」的函數,在寫入檔案時提供連續的行流,而不會阻塞主執行緒。

原始解決方案

提供的Go 程式碼使用非同步goroutine 不斷地監視文件中的新行,這會引發對慣用Go 風格和潛在過度複雜化的擔憂。

更簡潔的方法

更直接、更慣用的Go 方法包括創建一個包裝器僅在到達文件末尾時才休眠的文件讀取器:

<code class="go">type tailReader struct {
    io.ReadCloser
}

func (t tailReader) Read(b []byte) (int, error) {
    for {
        n, err := t.ReadCloser.Read(b)
        if n > 0 {
            return n, nil
        } else if err != io.EOF {
            return n, err
        }
        time.Sleep(10 * time.Millisecond)
    }
}</code>

用法

此包裝器可以在任何需要標準io.Reader 的地方使用。例如,要使用bufio.Scanner 循環行:

<code class="go">t, err := newTailReader("somefile")
if err != nil {
    log.Fatal(err)
}
defer t.Close()
scanner := bufio.NewScanner(t)
for scanner.Scan() {
    fmt.Println(scanner.Text())
}</code>

或者,閱讀器可用於​​更複雜的任務,例如處理附加的JSON 值:

<code class="go">t, err := newTailReader("somefile")
if err != nil {
    log.Fatal(err)
}
defer t.Close()
dec := json.NewDecoder(t)
for {
    var v SomeType
    if err := dec.Decode(&amp;v); err != nil {
       log.Fatal(err)
    }
    fmt.Println("the value is ", v)
}</code>

優點

這個方法有幾個優點:

  • 輕鬆關閉:只需關閉檔案即可停止讀取器。
  • 慣用的 Go 風格:它避免了對非同步 goroutine 的需要,這對於此任務來說是不必要的。
  • 相容性:包裝器可以與任何期望的程式碼一起使用io.Reader。
  • 可設定的睡眠時間:可以調整睡眠間隔以最佳化延遲或 CPU 使用率。

以上是如何在 Go 中建立“tail -f”等效項?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn