Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

reusing read buffers when working with sockets

Tags:

go

sockets

buffer

I'd like to know the proper way to reuse the []byte buffer in go. I declare it like this

buf := make([]byte, 1024)

and then use like this

conn, _ := net.Dial("tcp", addr)
_, err = conn.read(buf)

I heard that declaring a new buffer isn't efficient since it involves memory allocations and that we should reuse existing buffers instead. However I am not sure if I just can pass the buffer again and it will be wiped or it can hold parts of previous messages (especially if the current message from socket is shorter than prev.one)?

like image 930
Gonzalez Avatar asked Dec 06 '25 10:12

Gonzalez


2 Answers

The Read method reads up to the len(buf) bytes to the buffer and returns the number of bytes read.

The Read method does not modify length of the caller's slice. It cannot because the slice is passed by value. The application must use the returned length to get a slice of the bytes actually read.

n, err = conn.Read(buf)
bufRead := buf[:n]

The application can call Read multiple times using the the same buffer.

conn, err := net.Dial("tcp", addr)
if err != nil {
    // handle error
}

buf := make([]byte, 1024)
for {
    n, err = conn.Read(buf)
    if err != nil {
        // handle error
    }
    fmt.Printf("Read %s\n", buf[:n]) // buf[:n] is slice of bytes read from conn
}

In practice you rarely use io.Reader.Read(), instead you pipe it down where io.Reader needed in code. Buffer will not be wiped, you must do it by hand. Or if you want a buffer you can use bufio

conn, _ := net.Dial("tcp", addr)
r:=bufio.NewReader(conn)

which you can

r.WriteTo(io.Writer) //for example for further processing

and you can reset

r.Reset(NewConn)
like image 40
Uvelichitel Avatar answered Dec 08 '25 00:12

Uvelichitel



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!