forked from hashicorp/consul-template
/
set.go
72 lines (63 loc) · 1.28 KB
/
set.go
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
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
package dependency
import (
"strings"
"sync"
)
// Set is a dependency-specific set implementation. Relative ordering is
// preserved.
type Set struct {
once sync.Once
sync.RWMutex
list []string
set map[string]Dependency
}
// Add adds a new element to the set if it does not already exist.
func (s *Set) Add(d Dependency) bool {
s.init()
s.Lock()
defer s.Unlock()
if _, ok := s.set[d.String()]; !ok {
s.list = append(s.list, d.String())
s.set[d.String()] = d
return true
}
return false
}
// Get retrieves a single element from the set by name.
func (s *Set) Get(v string) Dependency {
s.RLock()
defer s.RUnlock()
return s.set[v]
}
// List returns the insertion-ordered list of dependencies.
func (s *Set) List() []Dependency {
s.RLock()
defer s.RUnlock()
r := make([]Dependency, len(s.list))
for i, k := range s.list {
r[i] = s.set[k]
}
return r
}
// Len is the size of the set.
func (s *Set) Len() int {
s.RLock()
defer s.RUnlock()
return len(s.list)
}
// String is a string representation of the set.
func (s *Set) String() string {
s.RLock()
defer s.RUnlock()
return strings.Join(s.list, ", ")
}
func (s *Set) init() {
s.once.Do(func() {
if s.list == nil {
s.list = make([]string, 0, 8)
}
if s.set == nil {
s.set = make(map[string]Dependency)
}
})
}