-2

I am confused about pass by value in Go. I am doing this;

package main

import (
    "fmt"
)

type point struct {
    x    int
    list []int
}

func main() {
    p := point{20, []int{1, 2, 3, 4, 5}}

    fmt.Printf("Address: %p, Value: %v\n", &p, p)
    passByValue(p, 1)
    fmt.Printf("Address: %p, Value: %v\n", &p, p)

}

func passByValue(copyOfP point, i int) {
    copyOfP.list = append(copyOfP.list[:i], copyOfP.list[i+1:]...)
    fmt.Printf("From passByValue Address: %p, Value: %v\n", &copyOfP, copyOfP)
}

Output:

Original p Address: 0xc00000c080, Value: {20 [1 2 3 4 5]}
passByValue copyOfP Address: 0xc00000c0c0, Value: {20 [1 3 4 5]}
Original p Address: 0xc00000c080, Value: {20 [1 3 4 5 5]}

shouldn't copyOfP be a copy of p and not reflect on original p what so ever.

Whats happening here?

Nagri
  • 3,008
  • 5
  • 34
  • 63

1 Answers1

1
func main() {

    // history.ReadlineTest()

    p := point{20, []int{1, 2, 3, 4, 5}}

    fmt.Printf("Address: %p, Value: %v\n", &p.list[0], p)
    passByValue(p, 1)
    fmt.Printf("Address: %p, Value: %v\n", &p.list[0], p)
}

func passByValue(copyOfP point, i int) {
    copyOfP.list = append(copyOfP.list[:i], copyOfP.list[i+1:]...)
    fmt.Printf("From passByValue Address: %p, Value: %v\n", &copyOfP.list[0], copyOfP)
}
Address: 0xc00001a0c0, Value: {20 [1 2 3 4 5]}
From passByValue Address: 0xc00001a0c0, Value: {20 [1 3 4 5]}
Address: 0xc00001a0c0, Value: {20 [1 3 4 5 5]}

The "list" slice reused the same memory.

p1gd0g
  • 631
  • 5
  • 16
  • Awesome. What would be the way to make a true copy of this struct that don't overlap what so ever? – Nagri Apr 08 '20 at 12:55
  • @Nagri It depends. A possible but not recommended way is to marshal and unmarshal your point. – p1gd0g Apr 08 '20 at 13:09
  • 3
    @Nagri: for solutions, look for "deep copy" for Go, like this answer https://stackoverflow.com/questions/46790190/quicker-way-to-deepcopy-objects-in-golang or this post: https://flaviocopes.com/go-copying-structs/ – Eli Bendersky Apr 08 '20 at 13:41