• Map声明、元素访问及遍历、⼯⼚模式、实现 Set - GO语言从入门到实战


    Map声明、元素访问及遍历 - GO语言从入门到实战

    Map 声明的方式
    m := map[string]int{"one": 1, "two": 2, "three": 3}  	
    //m初始化时就已经设置了3个键值对,所以它的初始长度len(m)是3。
    
    m1 := map[string]int{}  
    //m1被初始化为一个空的map,然后通过m1["one"] = 1添加了一个键值对,所以它的初始长度len(m1)是1。
    
    m2 := make(map[string]int, 10)
    //使用make函数创建了一个具有初始容量10的map。这里的初始容量(capacity)并不是map的长度(len),但它决定了map可以在不重新分配内存的情况下存储的键值对的最大数量。也就是说,虽然指定了初始容量为10,但map的实际长度(即存储的键值对的数量)可以为0,并可以随着你添加键值对而增加,直到达到容量限制。欢迎关注云尔Websites CSDN博客
    //len(m2)将返回0(因为你还没有向m2中添加任何键值对)。
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    这块知识一定要多敲代码,运行看看,才能加深理解。
    代码示例:

    package my_map  
      
    import "testing"  
      
    func TestInitMap(t *testing.T) {  
    	 m1 := map[int]int{1: 2, 2: 3, 3: 4}  
    	 if v, ok := m1[2]; ok {  
    	 	t.Logf("m1[2] = %d", v)  
    	 } else {  
    	 	t.Error("Key 2 does not exist in m1")  
    	 }  
    	 t.Logf("len m1 = %d", len(m1))  
    	  
    	 m2 := map[int]int{}  
    	 m2[4] = 16  
    	 t.Logf("len m2 = %d", len(m2))  
    	  
    	 m3 := make(map[int]int, 10)  
    	 t.Logf("len m3 = %d", len(m3))  
    }  
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    Map 元素的访问

    与其他主要编程语⾔的差异
    在访问的 Key 不存在时,仍会返回零值,不能通过返回 nil 来判断元素是否存在。欢迎关注云尔Websites CSDN博客
    优点: 可以避免在访问不存在的键时发生运行时错误,从而使代码更安全。
    缺点: 可能会使代码变得更复杂,因为我们必须显式地检查键是否存在

    
    func TestAccessNotExistingKey(t *testing.T) {  
    
    	m := map[string]int{}
    	if v, k := m["four"]; k {
     		t.Logf("m[1] = %d", v)  
    	} else {
    		t.Log("欢迎关注云尔Websites CSDN博客")  
    	}
    
    	 m1 := map[int]int{}  
    	  
    	 if v, k := m1[1]; k {  
    	 	t.Logf("m1[1] = %d", v)  
    	 } else {  
    	 	t.Log("Key 1 does not exist in m1")  
    	 }  
    	  
    	 m1[2] = 0  
    	 if v, k := m1[2]; k {  
    	 	t.Logf("m1[2] = %d", v)  
    	 } else {  
    	 	t.Error("Key 2 does not exist in m1")  
    	 }  
    	  
    	 m1[3] = 0  
    	 if v, k := m1[3]; k {  
    	 	t.Logf("Key 3's value is %d", v)  
    	 } else {  
    	 	t.Log("Key 3 does not exist in m1")  
    	 }  
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    Map 遍历

    遍历在之前文章里面说过,这里简单说下:
    可以使用range关键字来遍历map。range会返回两个值:键和值。请注意,遍历map的顺序是不确定的,因为map是无序的数据结构。欢迎关注云尔Websites CSDN博客

    package main  
      
    import "fmt"  
      
    func main() {  
    	 m := map[string]int{"one": 1, "two": 2, "three": 3}
    	 // 使用range遍历map  
    	 for key, value := range m {  
    	 	fmt.Printf("Key: %s, Value: %d\n", key, value)  
    	 }  
    }
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    Map 扩展知识

    Map 与⼯⼚模式

    Map 的 value 可以是任何类型,包括方法。
    与 Go 的 Dock type 接⼝⽅式⼀起,可以⽅便的实现单⼀⽅法对象的⼯⼚模式,可以将一个方法的名称(或其他唯一标识符)映射到一个具体的方法实现上。
    代码示例:

    package main  
      
    import "fmt"  
      
    type Calculator interface {  
     	Calculate(int, int) int  
    }  
      
    type Adder struct{}  
      
    func (a Adder) Calculate(x, y int) int {  
     	return x + y  
    }  
      
    type Subtracter struct{}  
      
    func (s Subtracter) Calculate(x, y int) int {  
     	return x - y  
    }  
      
    type Multiplier struct{}  
      
    func (m Multiplier) Calculate(x, y int) int {  
     	return x * y  
    }  
      
    func main() {  
    	 calculators := map[string]Calculator{  
    	 "add":     Adder{},  
    	 "subtract": Subtracter{},  
    	 "multiply": Multiplier{},  
     }  
      
     for operation, calculator := range calculators {  
    	 result := calculator.Calculate(5, 3)  
    	 fmt.Printf("%s 5 and 3 gives: %d\n", operation, result)  
     }  
    }
    
    //在上面的示例中,定义了一个Calculator接口,它包含一个Calculate方法。然后创建了三个结构体(Adder、Subtracter和Multiplier),并为它们分别实现了Calculate方法。接下来创建了一个Map,将字符串映射到实现了Calculator接口的对象。最后使用for循环遍历Map,并根据操作类型执行相应的计算。
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    通过Map实现 Set

    Go 的内置集合中没有 Set 实现, 可以 map[type]bool来写。

    1. 元素的唯⼀性,由于map的键必须是唯一的,所以使用map[type]bool可以确保Set中的元素也是唯一的;
    2. 基本操作:添加元素、判断元素是否存在、删除元素、获取元素个数。
    //添加元素:
    //创建了一个新的map(如果s尚未创建),并将element添加到Set中。
    s := make(map[T]bool)  
    s[element] = true
    
    //判断元素是否存在:
    //检查element是否存在于Set中。如果存在,exists将为true;否则为false。
    _, exists := s[element]
    
    //删除元素:
    //从Set中删除element。
    delete(s, element)
    
    //元素个数:
    //返回Set中的元素个数。
    len(s)
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    通过Map实现 Set 的代码示例:

    
    package map_ext
    
    import "testing"
    
    // TestMapWithFunValue 测试使用函数作为值的map
    func TestMapWithFunValue(t *testing.T) {
    	 m := make(map[int]func(op int) int)
    	 m[1] = func(op int) int { return op }
    	 m[2] = func(op int) int { return op * op }
    	 m[3] = func(op int) int { return op * op * op }
    	
    	 result1 := m[1](2)
    	 result2 := m[2](2)
    	 result3 := m[3](2)
    	
    	 t.Logf("%d, %d, %d", result1, result2, result3)
    }
    
    // TestMapForSet 测试使用map实现集合功能
    func TestMapForSet(t *testing.T) {
    	 mySet := make(map[int]bool)
    	 mySet[1] = true
    	
    	 n := 3
    	 if mySet[n] {
    	 	t.Logf("%d已存在", n)
    	 } else {
    	 	t.Logf("%d不存在", n)
    	 }
    	
    	 mySet[3] = true
    	 t.Logf("集合长度:%d", len(mySet))
    	
    	 delete(mySet, 1)
    	 n = 1
    	 if mySet[n] {
    	 	t.Logf("%d已存在", n)
    	 } else {
    	 	t.Logf("%d不存在", n)
    	 }
    }
    
    这里是一些需要注意的点:
    1. 使用`make`函数初始化map,以明确其类型。
    2. 为函数值定义了一个map,并存储了几个不同的函数。
    3. 使用`delete`函数从map中删除一个键值对。
    
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48

    Map声明、元素访问及遍历 - GO语言从入门到实战

    学习Go语言主要是多练,多找些代码段写写,不懂可以私聊咨询。

    欢迎关注云尔Websites CSDN博客

  • 相关阅读:
    burp || Note: Disk-based projects are onlysupported on Burp Suite Professional
    2023秋招——大数据研发工程师提前批一面
    【Java项目】讲讲我用Java爬虫获取LOL英雄数据与图片(附源码)
    支持typecho博客的黑白模式纪念日插件
    IDEA新建SpringBoot项目时启动编译报错:Error:java: 无效的源发行版: 17
    照片+制作照片书神器,效果太棒了!
    个人博客网站一揽子:Docker搭建图床(Lsky Pro)
    Google-CTF-2016-Stego.pcap数据包解析
    springboot整合支付宝沙箱支付
    布隆过滤器Bloom Filter
  • 原文地址:https://blog.csdn.net/wuchengzeng/article/details/133554741