阅读超出缓冲区

I have a buffer of size bufferSize from which I read in chunks of blockSize, however, this yields some (to me) unexpected behavior, when the blockSize goes beyond the bufferSize.

I've put the code here:

http://play.golang.org/p/Ra2jicYHPu

Why does the second chunk only give 4 bytes? What's happening here?

I'd expect Read to always give the amount of bytes len(byteArray), and if it goes beyond the buffer, it'll handle that situation by setting the pointer in the buffer to after byteArray, and putting the rest of the buffer + whatever is beyond until the new buffer pointer.

Your expectations are not based on any documented behavior of bufio.Reader. If you want "Read to always give the amount of bytes len(byteArray)" you must use io.ReadAtLeast.

package main

import (
        "bufio"
        "fmt"
        "io"
        "strings"
)

const bufSize = 10
const blockSize = 12

func main() {
        s := strings.NewReader("some length test string buffer boom")
        buffer := bufio.NewReaderSize(s, bufSize)

        b := make([]byte, blockSize)
        n, err := io.ReadAtLeast(buffer, b, blockSize)
        if err != nil {
                fmt.Println(err)
        }

        fmt.Printf("First read got %d bytes: %s
", n, string(b))

        d := make([]byte, blockSize)
        n, err = io.ReadAtLeast(buffer, d, blockSize)
        if err != nil {
                fmt.Println(err)
        }

        fmt.Printf("Second read got %d bytes: %s
", n, string(d))
}

Playground


Output:

First read got 12 bytes: some length 
Second read got 12 bytes: test string 

1.see the code of buffio.NewReaderSize

func NewReaderSize(rd io.Reader, size int) *Reader {
    // Is it already a Reader?
    b, ok := rd.(*Reader)
    if ok && len(b.buf) >= size {
        return b
    }
    if size < minReadBufferSize {
        size = minReadBufferSize
    }
    return &Reader{
        buf:          make([]byte, size),
        rd:           rd,
        lastByte:     -1,
        lastRuneSize: -1,
    }
}

strings.NewReader return a strings.Reader,so the buffer's (returned by bufio.NewReaderSize ) buf has minReadBufferSize(val is 16) 2.see code of bufio.Read

func (b *Reader) Read(p []byte) (n int, err error) {
    ……
    copy(p[0:n], b.buf[b.r:])
    b.r += n
    b.lastByte = int(b.buf[b.r-1])
    b.lastRuneSize = -1
    return n, nil
}

copy src is b.buf[b.r:],when your first Read,b.r=12,……