缓存功能

    1. [bufio]
    2. producer --> buffer --> io.Writer
    3. [Reader]
    4. [Writer]
    5. bufio.Writer 底层使用 []byte 进行缓存
    6. bufio.Writer 默认使用 4096 长度字节的缓存,可以使用 NewWriterSize 方法来设定该值
    7. [Scanner]
    8. [重置]
    9. Reset
    10. [缓存剩余空间]
    11. Available
    package main
    
    import (
        "bufio"
        "fmt"
    )
    
    type Writer int
    
    func (*Writer) Write(p []byte) (n int, err error) {
        fmt.Println(len(p))
        return len(p), nil
    }
    func main() {
        // 没有被缓存的 I/O,意味着每一次写操作都将直接写入目的地
      // 我们进行4次写操作,每次写操作都映射为对 Write 的调用,调用时传入的参数为一个长度为1的 byte 切片
        fmt.Println("Unbuffered I/O")
        w := new(Writer)
        w.Write([]byte{'a'})
        w.Write([]byte{'b'})
        w.Write([]byte{'c'})
        w.Write([]byte{'d'})
    
      // 使用缓存的I/O,使用三个字节长度的缓存来存储数据,当缓存满时进行一次 flush 操作(数据处理)
      // 前三次写入写满了缓存,第四次写入时检测到缓存没有剩余空间,所以将缓存中的积累的数据写出
      // 字母 d 被存储了,但在此之前 Flush 被调用以腾出空间,当缓存被写到末尾时,缓存中未被处理的数据需要被处理
      // bufio.Writer 仅在缓存充满或者显式调用 Flush 方法时处理(发送)数据。
        fmt.Println("Buffered I/O")
        bw := bufio.NewWriterSize(w, 3)
        bw.Write([]byte{'a'})
        bw.Write([]byte{'b'})
        bw.Write([]byte{'c'})
        bw.Write([]byte{'d'})
        err := bw.Flush()
        if err != nil {
            panic(err)
        }
    }
    
    // 实现原理
    type Writer struct {
        err error
        buf []byte
        n   int
        wr  io.Writer
    }
    
    // 字段 buf 用来存储数据,当缓存满或者 Flush 被调用时,消费者(wr)可以从缓存中获取到数据。
    // 如果写入过程中发生了 I/O error,此 error 将会被赋给 err 字段,error 发生之后,writer 将停止操作
    
    type Writer int
    func (*Writer) Write(p []byte) (n int, err error) {
        fmt.Printf("Write: %q\n", p)
        return 0, errors.New("boom!")
    }
    func main() {
        w := new(Writer)
        bw := bufio.NewWriterSize(w, 3)
        bw.Write([]byte{'a'})
        bw.Write([]byte{'b'})
        bw.Write([]byte{'c'})
        bw.Write([]byte{'d'})
        err := bw.Flush()
        fmt.Println(err)
    }