map中的结构体元素是无法取地址的,即:map[string]struct类型,取&map[“tmp”]是错误的。会提示报错:
???cannot assign to struct field elem["count"].count in map。
原因为:map中的元素并不是一个变量,而是一个值。因此,我们不能对map的元素进行取址操作。
1.使用示例一:map对应的值为结构体类型的值
package main
import (
"fmt"
"time"
)
// Counter 代表计数器的类型。
type Counter struct {
count int
}
var mapChan = make(chan map[string]Counter, 1)
func main() {
syncChan := make(chan struct{}, 2)
go func() { // 接收操作
for {
if elem, ok := <-mapChan; ok {
counter := elem["count"] //传值
counter.count++
fmt.Printf("[receiver] The elem is: %v. Elem address: %p
", elem, &elem)
fmt.Printf("[receiver] The counter: %d.
", counter.count)
/*
map中的结构体元素是无法取地址的,即:map[string]struct类型,取&map["tmp"]是错误的.
使用下面的语句,会报提示语 cannot assign to struct field elem["count"].count in map.
*/
//elem["count"].count++
//fmt.Printf("[receiver] The elem is: %v. Elem address: %p
", elem, &elem)
//fmt.Printf("[receiver] The counter: %d.
", elem["count"].count)
} else {
break
}
}
fmt.Println("[receiver] Stopped.")
syncChan <- struct{}{} // 发送同步通知
}()
go func() { // 发送操作
countMap := map[string]Counter{
"count": Counter{},
}
for i := 0; i < 5; i++ {
mapChan <- countMap
time.Sleep(time.Millisecond)
fmt.Printf("[sender] The count map: %v. Count map address: %p
", countMap, &countMap)
fmt.Printf("[sender] The counter: %d.
", countMap["count"].count)
}
close(mapChan)
syncChan <- struct{}{} // 发送同步通知
}()
<-syncChan //接收同步通知
<-syncChan //接收同步通知
}
运行结果如下所示:
[receiver] The elem is: map[count:{0}]. Elem address: 0xc000078000
[receiver] The counter: 1.
[sender] The count map: map[count:{0}]. Count map address: 0xc00000c030
[sender] The counter: 0.
[receiver] The elem is: map[count:{0}]. Elem address: 0xc000078010
[receiver] The counter: 1.
[sender] The count map: map[count:{0}]. Count map address: 0xc00000c030
[sender] The counter: 0.
[receiver] The elem is: map[count:{0}]. Elem address: 0xc0000a0000
[receiver] The counter: 1.
[sender] The count map: map[count:{0}]. Count map address: 0xc00000c030
[sender] The counter: 0.
[receiver] The elem is: map[count:{0}]. Elem address: 0xc00000c040
[receiver] The counter: 1.
[sender] The count map: map[count:{0}]. Count map address: 0xc00000c030
[sender] The counter: 0.
[receiver] The elem is: map[count:{0}]. Elem address: 0xc000078020
[receiver] The counter: 1.
[sender] The count map: map[count:{0}]. Count map address: 0xc00000c030
[sender] The counter: 0.
[receiver] Stopped.
2. 使用示例二:map对应的值为结构体类型的指针
package main
import (
"fmt"
"time"
)
// Counter 代表计数器的类型。
type Counter struct {
count int
}
// 注意:map对应的值为地址(指针)
var mapChan = make(chan map[string]*Counter, 1)
func main() {
syncChan := make(chan struct{}, 2)
go func() { // 接收操作
for {
if elem, ok := <-mapChan; ok {
counter := elem["count"] //传地址
counter.count++
fmt.Printf("[receiver] The elem is: %v. Elem address: %p
", elem, &elem)
fmt.Printf("[receiver] The counter: %d.
", counter.count)
/*
map中的元素是无法取地址的,即:map[string]struct类型,取&map["tmp"]是错误的.
使用下面的语句,会报提示语 cannot assign to struct field elem["count"].count in map.
*/
//elem["count"].count++
//fmt.Printf("[receiver] The elem is: %v. Elem address: %p
", elem, &elem)
//fmt.Printf("[receiver] The counter: %d.
", elem["count"].count)
} else {
break
}
}
fmt.Println("[receiver] Stopped.")
syncChan <- struct{}{}
}()
go func() { // 发送操作
countMap := map[string]*Counter{
"count": &Counter{},
}
for i := 0; i < 5; i++ {
mapChan <- countMap
time.Sleep(time.Millisecond)
fmt.Printf("[sender] The count map: %v. Count map address: %p
", countMap, &countMap)
fmt.Printf("[sender] The counter: %d.
", countMap["count"].count)
}
close(mapChan)
syncChan <- struct{}{}
}()
<-syncChan
<-syncChan
}
运行结果如下所示:
[receiver] The elem is: map[count:0xc000074008]. Elem address: 0xc00008a000
[receiver] The counter: 1.
[sender] The count map: map[count:0xc000074008]. Count map address: 0xc000082020
[sender] The counter: 1.
[receiver] The elem is: map[count:0xc000074008]. Elem address: 0xc00008a010
[receiver] The counter: 2.
[sender] The count map: map[count:0xc000074008]. Count map address: 0xc000082020
[sender] The counter: 2.
[receiver] The elem is: map[count:0xc000074008]. Elem address: 0xc00000c010
[receiver] The counter: 3.
[sender] The count map: map[count:0xc000074008]. Count map address: 0xc000082020
[sender] The counter: 3.
[receiver] The elem is: map[count:0xc000074008]. Elem address: 0xc00000c018
[receiver] The counter: 4.
[sender] The count map: map[count:0xc000074008]. Count map address: 0xc000082020
[sender] The counter: 4.
[receiver] The elem is: map[count:0xc000074008]. Elem address: 0xc00000c020
[receiver] The counter: 5.
[sender] The count map: map[count:0xc000074008]. Count map address: 0xc000082020
[sender] The counter: 5.
[receiver] Stopped.
3. 使用示例三:map对应的值为int类型
package main
import (
"fmt"
"time"
)
var mapChan = make(chan map[string]int, 1)
func main() {
syncChan := make(chan struct{}, 2)
go func() { // 接收操作
for {
if elem, ok := <-mapChan; ok { // 从通道中获取值
elem["count"]++
fmt.Printf("[receiver] The elem is: %v. Elem address is: %p
", elem, &elem)
} else {
break
}
}
fmt.Println("[receiver] Stopped.")
syncChan <- struct{}{} // 发送同步通知
}()
go func() { // 发送操作
countMap := make(map[string]int) // map为引用类型,发送和接收的元素为同一个值
for i := 0; i < 5; i++ {
countMap["count"]++
mapChan <- countMap // 向通道中输入值
time.Sleep(time.Millisecond)
fmt.Printf("[sender] The count map: %v. Count map address: %p
", countMap, &countMap)
}
close(mapChan) // 关闭通道
syncChan <- struct{}{} // 发送同步通知
}()
<-syncChan //接收同步通知
<-syncChan //接收同步通知
fmt.Println(" map为引用类型,发送和接收的元素指向同一个值.")
}
运行结果如下所示:
[receiver] The elem is: map[count:2]. Elem address is: 0xc000078000
[sender] The count map: map[count:2]. Count map address: 0xc00000c030
[receiver] The elem is: map[count:4]. Elem address is: 0xc000078010
[sender] The count map: map[count:4]. Count map address: 0xc00000c030
[receiver] The elem is: map[count:6]. Elem address is: 0xc00000c040
[sender] The count map: map[count:6]. Count map address: 0xc00000c030
[receiver] The elem is: map[count:8]. Elem address is: 0xc0000a4000
[sender] The count map: map[count:8]. Count map address: 0xc00000c030
[receiver] The elem is: map[count:10]. Elem address is: 0xc000078020
[sender] The count map: map[count:10]. Count map address: 0xc00000c030
[receiver] Stopped.
map为引用类型,发送和接收的元素指向同一个值.