【问题标题】:What value does the return value take if something is not in a map?如果地图中没有东西,返回值取什么值?
【发布时间】:2018-10-28 05:28:48
【问题描述】:

好的,按照这个:

How to check if a map contains a key in go?

if val, ok := m["foo"]; ok {
    //do something here
}

这很好,但是我们为什么不能这样做:

val, ok := m["foo"]

if val == nil {   // cannot compare val to nil

}

我收到一个编译错误,说我无法将 val 与 nil 进行比较,但是 val 有什么值?我可以将它与什么进行比较,以确定它是否存在?

m 的类型是这样的:

type m map[string]struct{}

【问题讨论】:

    标签: go


    【解决方案1】:

    The Go Programming Language Specification

    Index expressions

    对于映射类型 M 的 a:如果映射为 nil 或不包含这样的 条目,a[x] 是 M 的元素类型的零值。

    The zero value

    当为变量分配存储空间时,无论是通过声明 或调用 new,或在创建新值时,通过 复合文字或 make 调用,并且没有显式初始化 提供,变量或值被赋予默认值。每个元素 这样一个变量或值的类型被设置为零值: 布尔值为 false,数字类型为 0,字符串为 "",nil 为 指针、函数、接口、切片、通道和映射。


    The Go Programming Language Specification

    Composite literals

    复合字面量为结构、数组、切片和 映射并在每次评估时创建一个新值。它们包括 字面量的类型,后跟大括号绑定的元素列表。 每个元素可以可选地在一个相应的键之前。为了 结构文字适用以下规则:

    文字可以省略元素列表;这样的文字评估为 其类型的值为零。

    对于您的示例,键入 struct{},省略复合文字 struct{}{} 中的元素列表作为零值。

    例如,

    package main
    
    import "fmt"
    
    func main() {
        m := map[string]struct{}{}
        val, ok := m["foo"]
        fmt.Printf("%T %v\n", val, val)
        if val == struct{}{} {
            fmt.Println("==", val, ok)
        }
    }
    

    游乐场:https://play.golang.org/p/44D_ZfFDA77

    输出:

    struct {} {}
    == {} false
    

    The Go Programming Language Specification

    Variable declarations

    变量声明创建一个或多个变量,绑定 对应的标识符,并给每个人一个类型和一个 初始值。

    如果给出了表达式列表,则变量被初始化为 遵循分配规则的表达式。否则,每个 变量被初始化为零值。

    如果存在类型,则为每个变量指定该类型。否则, 每个变量都被赋予了相应的初始化类型 赋值中的值。

    在您的示例中,您可以声明一个没有初始值的 struct{} 类型的变量,该变量将被初始化为 struct{} 类型的零值。

    例如,

    package main
    
    import "fmt"
    
    func main() {
        m := map[string]struct{}{}
        val, ok := m["foo"]
        fmt.Printf("%T %v\n", val, val)
        var zeroValue struct{}
        if val == zeroValue {
            fmt.Println("==", val, ok)
        }
    }
    

    游乐场:https://play.golang.org/p/_XcSCEeEKJV

    输出:

    struct {} {}
    == {} false
    

    【讨论】:

    • 根据这个,结构的零值应该是零? stackoverflow.com/questions/28625794/…
    • @MrCholo:struct 的零值是其字段的零值的合成。
    • 啊嘘,这听起来不像nil 对我来说,这就是为什么我得到了我在 OP 中得到的东西
    • 我想知道composite of the zero values of its fields 的意义是什么,为什么不只是零?因为 NPE 不好?
    【解决方案2】:

    你肯定可以做你上面所做的。与 nil 的比较取决于您在 map 中具有的值的类型。如果是interface{},您可以将其与 nil 进行比较:

    m := map[string]interface{}{}
    
    val, _ := m["foo"]
    
    if val == nil {
        fmt.Println("no index")
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-02-20
      • 1970-01-01
      • 2023-04-10
      • 2023-02-07
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多