为了账号安全,请及时绑定邮箱和手机立即绑定

Go 中的哪些语义规则决定何时发生单值赋值与何时发生二值赋值?

Go 中的哪些语义规则决定何时发生单值赋值与何时发生二值赋值?

Go
长风秋雁 2022-06-27 10:12:05
map在学习A Tour of Go: Mutating Maps时,我发现令人惊讶的一件事是,我们可以使用单值赋值或双值赋值来访问映射中键的值。示例代码:package mainimport (    "fmt")func main() {    m := map[int]int{2: 4, 3: 9, 4: 16}        // Example 1    fmt.Println(m[2])        // Example 2    v := m[2]    fmt.Println(v)        // Example 3    v, ok := m[2]    fmt.Println(v, ok)}输出:444 true使用相同语法同时支持单值和双值赋值涉及哪些语义规则?Go 中是否还有其他这种特殊形式,根据赋值运算符的左侧,以相同的语法同时支持单值和双值赋值?此外,我可以自己编写一个函数foo(),根据赋值运算符的左侧返回一个值或两个值吗?
查看完整描述

1 回答

?
米琪卡哇伊

TA贡献1998条经验 获得超6个赞

映射索引操作的一两个值分配是一种特殊形式,为方便起见,不幸的是,它不能在“正常”分配中完成。


普通赋值表达式:

该规范对元组分配有以下说法:


元组赋值将多值运算的各个元素分配给变量列表。有两种形式。首先,右手操作数是单个多值表达式,例如函数调用、通道或映射操作或类型断言。左侧操作数的数量必须与值的数量相匹配。例如,如果 f 是一个返回两个值的函数,


x, y = f()


将第一个值分配给 x,将第二个值分配给 y。第二种形式,左边的操作数的个数必须等于右边的表达式的个数,每个表达式都必须是单值的,右边的第n个表达式赋值给左边的第n个操作数:


one, two, three = '一', '二', '三'


这不会为分配中值的数量留下任何歧义的余地。


一值或二值表达式:

有 4 种情况,表达式左侧同时允许一个值和两个值。其中三个是赋值表达式的特殊形式,最后一个是range子句。


索引表达式:


索引表达式被定义为 的形式a[x],地图除外:


在特殊形式的赋值或初始化中使用的 map [K]V 类型的映射 a 上的索引表达式


v, ok = a[x]

v, ok := a[x]

var v, ok = a[x]

产生一个额外的无类型布尔值。


接收运营商:


接收操作符也会发生同样的情况,通常格式为x <-ch:


在特殊形式的赋值或初始化中使用的接收表达式


x, ok = <-ch

x, ok := <-ch

var x, ok = <-ch

var x, ok T = <-ch

产生一个额外的无类型布尔结果,报告通信是否成功。


类型断言:


再一次提到类型断言中的特殊形式,通常是这样的形式:x.(T)


在特殊形式的赋值或初始化中使用的类型断言


v, ok = x.(T)

v, ok := x.(T)

var v, ok = x.(T)

var v, ok T1 = x.(T)

产生一个额外的无类型布尔值。


范围子句:


带有 range 子句的for 语句具有与之相关的更宽松的语言,因为它不是对正常赋值表达式的修改:


左侧的函数调用在每次迭代时评估一次。对于每次迭代,如果存在相应的迭代变量,则按如下方式生成迭代值:


Range expression                          1st value          2nd value


array or slice  a  [n]E, *[n]E, or []E    index    i  int    a[i]       E

string          s  string type            index    i  int    see below  rune

map             m  map[K]V                key      k  K      m[k]       V

channel         c  chan E, <-chan E       element  e  E

非赋值的用途:

如上所述,所有三种特殊形式仅用于作业。尝试在其他表达式(函数调用、返回等)中使用多值返回将失败,因为这些不是赋值并且不会从特殊形式中受益。


查看完整回答
反对 回复 2022-06-27
  • 1 回答
  • 0 关注
  • 110 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信