Can golang string slicing like buf = buf[n:]
cause memory leak in the underlying byte array?
If so, is it possible to get any information (like capacity, or base memory address) about the underlying byte array, in order to verify the leak?
Please see sample code below:
var buf string
func push(s string) {
buf += s
if len(buf) > 3 {
buf = buf[len(buf)-3:] // can this line leak memory in underlying byte array?
}
fmt.Printf("buf=[%v]\n", buf)
}
Run it on playground
No, this example can't cause a memory leak, since you need to allocate new strings each time you call push
. It's possible that some bytes will be kept around at times to reduce allocations, but how that works is an implementation detail that shouldn't be taken into consideration.
If you're thinking of a similar situation which can arise when you assign a result of a slice operation, but never append. There's no leak per say, as long as you understand the semantics of slicing.
s := make([]byte, 1024)
s = s[1000:]
fmt.Println(s, len(s), cap(s))
This example will leave the first 1000 bytes allocated, but inaccessible. The answer to this is simple, don't do that. It's not hard to avoid, and if you do need to ensure that you've released the underlying array, use copy
to move the bytes to a new slice.
This works the same with strings:
s = s[1020:]
// may leave the first 1000 bytes allocated
This is again fairly easy to see what's going on, and avoid. If you're using huge strings, you're often better off using []byte
anyway, where you have better control over allocation, and can copy the bytes when needed.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With