------------------------------------------------------------ 若是用於多例程,可使用下面的版本: ------------------------------------------------------------ package main import ( "fmt" "sort" "sync" ) type Set struct { sync.RWMutex m map[int]bool } // 新建集合對象 // 能夠傳入初始元素 func New(items ...int) *Set { s := &Set{ m: make(map[int]bool, len(items)), } s.Add(items...) return s } // 建立副本 func (s *Set) Duplicate() *Set { s.Lock() defer s.Unlock() r := &Set{ m: make(map[int]bool, len(s.m)), } for e := range s.m { r.m[e] = true } return r } // 添加元素 func (s *Set) Add(items ...int) { s.Lock() defer s.Unlock() for _, v := range items { s.m[v] = true } } // 刪除元素 func (s *Set) Remove(items ...int) { s.Lock() defer s.Unlock() for _, v := range items { delete(s.m, v) } } // 判斷元素是否存在 func (s *Set) Has(items ...int) bool { s.RLock() defer s.RUnlock() for _, v := range items { if _, ok := s.m[v]; !ok { return false } } return true } // 統計元素個數 func (s *Set) Count() int { s.Lock() defer s.Unlock() return len(s.m) } // 清空集合 func (s *Set) Clear() { s.Lock() defer s.Unlock() s.m = map[int]bool{} } // 空集合判斷 func (s *Set) Empty() bool { s.Lock() defer s.Unlock() return len(s.m) == 0 } // 獲取元素列表(無序) func (s *Set) List() []int { s.RLock() defer s.RUnlock() list := make([]int, 0, len(s.m)) for item := range s.m { list = append(list, item) } return list } // 獲取元素列表(有序) func (s *Set) SortedList() []int { s.RLock() defer s.RUnlock() list := make([]int, 0, len(s.m)) for item := range s.m { list = append(list, item) } sort.Ints(list) return list } // 並集 // 獲取 s 與參數的並集,結果存入 s func (s *Set) Union(sets ...*Set) { // 爲了防止多例程死鎖,不能同時鎖定兩個集合 // 因此這裏沒有鎖定 s,而是建立了一個臨時集合 r := s.Duplicate() // 獲取並集 for _, set := range sets { set.Lock() for e := range set.m { r.m[e] = true } set.Unlock() } // 將結果轉入 s s.Lock() defer s.Unlock() s.m = map[int]bool{} for e := range r.m { s.m[e] = true } } // 並集(函數) // 獲取全部參數的並集,並返回 func Union(sets ...*Set) *Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取並集 r := sets[0].Duplicate() for _, set := range sets[1:] { set.Lock() for e := range set.m { r.m[e] = true } set.Unlock() } return r } // 差集 // 獲取 s 與全部參數的差集,結果存入 s func (s *Set) Minus(sets ...*Set) { // 爲了防止多例程死鎖,不能同時鎖定兩個集合 // 因此這裏沒有鎖定 s,而是建立了一個臨時集合 r := s.Duplicate() // 獲取差集 for _, set := range sets { set.Lock() for e := range set.m { delete(r.m, e) } set.Unlock() } // 將結果轉入 s s.Lock() defer s.Unlock() s.m = map[int]bool{} for e := range r.m { s.m[e] = true } } // 差集(函數) // 獲取第 1 個參數與其它參數的差集,並返回 func Minus(sets ...*Set) *Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取差集 r := sets[0].Duplicate() for _, set := range sets[1:] { for e := range set.m { delete(r.m, e) } } return r } // 交集 // 獲取 s 與其它參數的交集,結果存入 s func (s *Set) Intersect(sets ...*Set) { // 爲了防止多例程死鎖,不能同時鎖定兩個集合 // 因此這裏沒有鎖定 s,而是建立了一個臨時集合 r := s.Duplicate() // 獲取交集 for _, set := range sets { set.Lock() for e := range r.m { if _, ok := set.m[e]; !ok { delete(r.m, e) } } set.Unlock() } // 將結果轉入 s s.Lock() defer s.Unlock() s.m = map[int]bool{} for e := range r.m { s.m[e] = true } } // 交集(函數) // 獲取全部參數的交集,並返回 func Intersect(sets ...*Set) *Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取交集 r := sets[0].Duplicate() for _, set := range sets[1:] { for e := range r.m { if _, ok := set.m[e]; !ok { delete(r.m, e) } } } return r } // 補集 // 獲取 s 相對於 full 的補集,結果存入 s func (s *Set) Complement(full *Set) { r := full.Duplicate() s.Lock() defer s.Unlock() // 獲取補集 for e := range s.m { delete(r.m, e) } // 將結果轉入 s s.m = map[int]bool{} for e := range r.m { s.m[e] = true } } // 補集(函數) // 獲取 sub 相對於 full 的補集,並返回 func Complement(sub, full *Set) *Set { r := full.Duplicate() sub.Lock() defer sub.Unlock() for e := range sub.m { delete(r.m, e) } return r } func main() { s1 := New(1, 2, 3, 4, 5, 6, 7, 8) s2 := New(3, 4, 5, 6) s3 := New(1, 2, 5, 6, 8, 9) // 建立 10 個 goroutine 同步操做 s2,看會不會死鎖 wg := sync.WaitGroup{} for i := 0; i < 10; i++ { wg.Add(1) go func(n int) { for i := 0; i < 100; i++ { s2.Union(s1) // 獲取並集 fmt.Printf("%2v:s2 + %v = %v\n", n, s1.SortedList(), s2.SortedList()) s2.Minus(s3) // 獲取差集 fmt.Printf("%2v:s2 - %v = %v\n", n, s3.SortedList(), s2.SortedList()) s2.Intersect(s1) // 獲取交集 fmt.Printf("%2v:s2 * %v = %v\n", n, s1.SortedList(), s2.SortedList()) s2.Complement(s1) // 獲取 s2 相對於 s1 的補集 fmt.Printf("%2v:%v / s2 = %v\n", n, s1.SortedList(), s2.SortedList()) } wg.Done() }(i) } wg.Wait() } ------------------------------------------------------------ 若是不用於多例程,可使用下面的簡單版本: ------------------------------------------------------------ package main import ( "fmt" "sort" ) type Set map[int]bool // 新建集合對象 // 能夠傳入初始元素 func New(items ...int) Set { s := make(Set, len(items)) s.Add(items...) return s } // 建立副本 func (s Set) Duplicate() Set { r := make(map[int]bool, len(s)) for e := range s { r[e] = true } return r } // 添加元素 func (s Set) Add(items ...int) { for _, v := range items { s[v] = true } } // 刪除元素 func (s Set) Remove(items ...int) { for _, v := range items { delete(s, v) } } // 判斷元素是否存在 func (s Set) Has(items ...int) bool { for _, v := range items { if _, ok := s[v]; !ok { return false } } return true } // 統計元素個數 func (s Set) Count() int { return len(s) } // 清空集合 func (s Set) Clear() { s = map[int]bool{} } // 空集合判斷 func (s Set) Empty() bool { return len(s) == 0 } // 獲取元素列表(無序) func (s Set) List() []int { list := make([]int, 0, len(s)) for item := range s { list = append(list, item) } return list } // 獲取元素列表(有序) func (s Set) SortedList() []int { list := s.List() sort.Ints(list) return list } // 並集 // 獲取 s 與參數的並集,結果存入 s func (s Set) Union(sets ...Set) { for _, set := range sets { for e := range set { s[e] = true } } } // 並集(函數) // 獲取全部參數的並集,並返回 func Union(sets ...Set) Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取並集 r := sets[0].Duplicate() for _, set := range sets[1:] { for e := range set { r[e] = true } } return r } // 差集 // 獲取 s 與全部參數的差集,結果存入 s func (s Set) Minus(sets ...Set) { for _, set := range sets { for e := range set { delete(s, e) } } } // 差集(函數) // 獲取第 1 個參數與其它參數的差集,並返回 func Minus(sets ...Set) Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取差集 r := sets[0].Duplicate() for _, set := range sets[1:] { for e := range set { delete(r, e) } } return r } // 交集 // 獲取 s 與其它參數的交集,結果存入 s func (s Set) Intersect(sets ...Set) { for _, set := range sets { for e := range s { if _, ok := set[e]; !ok { delete(s, e) } } } } // 交集(函數) // 獲取全部參數的交集,並返回 func Intersect(sets ...Set) Set { // 處理參數數量 if len(sets) == 0 { return New() } else if len(sets) == 1 { return sets[0] } // 獲取交集 r := sets[0].Duplicate() for _, set := range sets[1:] { for e := range r { if _, ok := set[e]; !ok { delete(r, e) } } } return r } // 補集 // 獲取 s 相對於 full 的補集,結果存入 s func (s Set) Complement(full Set) { r := s.Duplicate() s.Clear() for e := range full { if _, ok := r[e]; !ok { s[e] = true } } } // 補集(函數) // 獲取 sub 相對於 full 的補集,並返回 func Complement(sub, full Set) Set { r := full.Duplicate() for e := range sub { delete(r, e) } return r } func main() { s1 := New(1, 2, 3, 4, 5, 6, 7, 8) s2 := New(3, 4, 5, 6) s3 := New(5, 6, 8, 9) r1 := Union(s1, s2, s3) // 獲取並集 r2 := Minus(s1, s2, s3) // 獲取差集 r3 := Intersect(s1, s2, s3) // 獲取交集 r4 := Complement(s2, s1) // 獲取 s2 相對於 s1 的補集 fmt.Println(r1.SortedList()) fmt.Println(r2.SortedList()) fmt.Println(r3.SortedList()) fmt.Println(r4.SortedList()) }