将值设置为结构作为映射中的值时,为什么会出现“cannot assign”错误?
技术问答
383 人阅读
|
0 人回复
|
2023-09-12
|
新的。遇到这个错误,却找不到原因或理由:- @6 S9 T% X+ f" O
如果我创建了一个结构,我显然可以毫无问题地分配和重新分配值:7 T6 ], |! R: \* O2 C- G2 D
type Person struct { name string age int}func main() { x := Person{"Andy Capp",98} x.age = 99 fmt.Printf("age: %d\n",x.age)}7 i! o* `* y1 ]- t* O! r3 i
但如果结构是地图上的一个值:
+ w# o& i& I. S+ ftype Person struct name string age int }type People map[string]Personfunc main() { p := make(People) p["HM"] = Person{"Hank McNamara",39} p["HM"].age = p["HM"].age 1 fmt.Printf("age: %d\n",p["HM"].age)}3 ?7 H; f; e$ q. y
我明白了cannot assign to p["HM"].age。没有其他信息。http://play.golang.org/p/VRlSItd4eP
$ F" B9 z8 I4 o I( r我找到了解决这个问题的方法 -incrementAge在 Person 创建一个func,它可以调用并将结果分配给映射键,例如p["HM"] = p["HM"].incrementAge().( W- e: v0 Y# E7 U% V
但我的问题是,这个不能分配错误的原因是什么,为什么不允许我直接分配结构值呢?$ M6 e! x0 d/ Q. d
' x# z6 T! L* D' H' d
解决方案: ) l0 i3 h( |7 c3 }. [9 Q7 j( N
p["HM"]不是常规的可寻址值:hashmap 可以在运行过程中生长,然后它们的值在内存中移动,旧位置过时。如果映射中的值被视为传统的可搜索值,则map实现的内部结构就会暴露出来。
& Q4 A, _3 v" E% q因此,在规范中p["HM"]称为地图索引表达式的东西略有不同;如果你在标准中搜索短语索引表达式,你会发现你可以对它们进行一些操作,比如读取它们,分配给它们,并在增量/减量表达式中使用它们(数字类型)。但你不能做任何事。他们本可以选择比他们更好更多的特殊情况,但我猜他们不仅仅是为了让事情变得简单。
; `3 K, ?' ~* U" X/ t8 i4 p你的方法在这里看起来不错——你把它改成常规分布,这是特别允许的操作之一。另一种方法(可能适用于你想避免复制的大结构?)使映射值成为常规的旧指针,可以通过以下方式修改底部对象:
( g! ^" x* v& _ M+ p: X2 ppackage mainimport "fmt"type Person struct name string age int}type People map[string]*Personfunc main() p := make(People) p["HM"] = &erson{"Hank McNamara",39} p["HM"].age = 1 fmt.Printf("age: %d\n",p["HM"].age)}
D$ A8 Z1 f0 ? |
|
|
|
|
|