焦點熱議:巧用 Go Map 特性對數組或切片去重

2022-12-12 11:01:57 來源:51CTO博客


(資料圖片)

耐心和持久勝過激烈和狂熱。

哈嘍大家好,我是陳明勇,今天分享的內容是巧用 Go Map 特性對數組或切片進行去重。如果本文對你有幫助,不妨點個贊,如果你是 Go 語言初學者,不妨點個關注,一起成長一起進步,如果本文有錯誤的地方,歡迎指出!

前言

在其他語言里(如 ??Java??? )使用過 ??Set??? 集合的小伙伴都知道,它的一個特點就是集合里的元素是不重復的。在一些需要去重場景中,我們可以使用 ??Set??? 這種數據結構去存儲數據,達到去重的目的。而在 ??Go??? 語言里面,是沒有 ??Set?? 這種數據類型的。如果我們想利用無重復元素的數據結構對數組或切片去重,可以使用 ??Go??? 的復合數據類型 ??Map??? 去構建 ??Set??? 集合,對數組或切片進行去重。因為 ??Map??? 中的 ??key??? 是唯一的,如果不了解 ??Map??? 的小伙伴,可以看看我的這篇文章 ??一文了解 Go 的復合數據類型(數組、Slice 切片、Map)??。

使用 Map 構建 Set

type MySet map[any]struct{}

定義一個自定義類型 ??MySet??? ,具有 ??map[any]strcut{}?? 的特性。

??map??? 的 ??key??? 是 ??any??? 類型,任何類型都可以當做 ??map??? 的 ??key??;??map??? 的 ??value??? 是 ??struct{}??? 類型,為什么會用結構體類型?是因為后面添加 ??k-v??? 鍵值對時,指定的 ??value??? 為 空結構體 ??strcut{}{}???,??fmt.Println(unsafe.Sizeof(struct{}{})) // 0?? 空結構體是不占用內存空間的。

對數組或切片去重

import "fmt"type MySet map[any]struct{}func main() {  s1 := []int{1, 1, 2, 3}  fmt.Println(duplicateRemoving(s1)) // [1 2 3]  s2 := []string{"a", "b", "c", "a"}  fmt.Println(duplicateRemoving(s2)) // [a b c]}func duplicateRemoving[T any](s []T) []T {  res := make([]T, 0, len(s))  mySet := make(MySet)  for _, t := range s {    if _, ok := mySet[t]; !ok {      res = append(res, t)      mySet[t] = struct{}{}    }  }  return res}

核心思路

定義一個新的切片 ??res???,為去重后的切片;定義一個 ??MySet ??? 類型的變量 ??mySet??,用于判斷元素是否重復;遍歷原切片 ??s???,首先判斷 ??mySet??? 里是否存在以切片 ??s??? 的元素 ??t??? 為 ??key??? 的鍵值對,如果不存在,往新切片 ??res??? 添加元素 ??t???,往 ??mySet??? 里添加鍵值對 ??t → struct{}{}??,否則說明元素重復,不做添加操作;返回去重后的新切片。

小結

本文介紹了如何利用 ??Go??? 的復合數據類型 ??Map??? 的特性對數組或切片進行去重。值得注意的一個地方是,在使用 ??Map??? 構建 ??Set??? 時,??Value??? 的數據類型指定為 ??struct{}???,原因是后面在添加鍵值對的時候,指定的 ??Value??? 為空結構體 ??strcut{}{}??,空結構體不占用內存空間。

標簽: 數據類型 數據結構 存儲數據

上一篇:天天快報!Linux系統如何知道端口號殺死進程
下一篇:世界觀點:非常流行且實用的5種軟件測試模型