地图是通过价值或Go中的参考传递的吗?

问题描述 投票:40回答:3

Go中的值是通过值传递还是引用?

始终可以将函数定义如下,但这是否过度?

func foo(dat *map[string]interface{}) {...}

返回值的问题相同。我应该返回指向地图的指针,还是将地图作为值返回?

目的当然是避免不必要的数据复制。

go
3个回答
37
投票

在这个帖子中你会找到你的答案:

Golang: Accessing a map using its reference

您不需要使用带有地图的指针。

地图类型是引用类型,如指针或切片[1]

如果您需要更改Session,可以使用指针:

map[string]*Session

https://blog.golang.org/go-maps-in-action


6
投票

以下是来自Dave Chaney的If a map isn’t a reference variable, what is it?的部分内容:

映射值是指向runtime.hmap结构的指针。

和结论:

结论

地图,如通道,但不像切片,只是指向运行时类型的指针。如上所述,map只是指向runtime.hmap结构的指针。

映射与Go程序中的任何其他指针值具有相同的指针语义。除了编译器将地图语法重写为对runtime / hmap.go中的函数的调用之外,没有什么神奇之处。

关于map语法的历史/解释,有趣的是:

如果地图是指针,它们不应该是* map [key]值吗?

这是一个很好的问题,如果map是指针值,为什么表达式make(map [int] int)返回一个类型为map [int] int的值。它不应该返回* map [int] int吗? Ian Taylor answered this recently in a golang-nuts thread1。

在早期我们称之为map的地方现在被写为指针,所以你写了* map [int] int。当我们意识到没有人写过map而没有写*map时,我们就离开了。

可以说,将类型从* map [int] int重命名为map [int] int,虽然因为类型看起来不像指针而混淆,但是比不能解除引用的指针形状值更容易混淆。


0
投票

默认情况下,没有地图参考。

    package main

    import "fmt"

    func mapToAnotherFunction(m map[string]int) {
        m["hello"] = 3
        m["world"] = 4
        m["new_word"] = 5
    }

    // func mapToAnotherFunctionAsRef(m *map[string]int) {
    // m["hello"] = 30
    // m["world"] = 40
    // m["2ndFunction"] = 5
    // }

    func main() {
        m := make(map[string]int)
        m["hello"] = 1
        m["world"] = 2

        // Initial State
        for key, val := range m {
            fmt.Println(key, "=>", val)
        }

        fmt.Println("-----------------------")

        mapToAnotherFunction(m)
        // After Passing to the function as a pointer
        for key, val := range m {
            fmt.Println(key, "=>", val)
        }

        // Try Un Commenting This Line
        fmt.Println("-----------------------")

        // mapToAnotherFunctionAsRef(&m)
        // // After Passing to the function as a pointer
        // for key, val := range m {
        //  fmt.Println(key, "=>", val)
        // }

        // Outputs
        // prog.go:12:4: invalid operation: m["hello"] (type *map[string]int does not support indexing)
        // prog.go:13:4: invalid operation: m["world"] (type *map[string]int does not support indexing)
        // prog.go:14:4: invalid operation: m["2ndFunction"] (type *map[string]int does not support indexing)

    }

从Golang Blog-

地图类型是引用类型,如指针或切片,因此上面的m值为nil;它没有指向初始化的地图。在读取时,nil映射的行为类似于空映射,但尝试写入nil映射将导致运行时出现混乱。不要那样做。要初始化地图,请使用内置的make函数:

m = make(map[string]int)

Code Snippet Link玩它。

© www.soinside.com 2019 - 2024. All rights reserved.