github.com/terramate-io/tf@v0.0.0-20230830114523-fce866b4dfcd/addrs/set.go (about)

     1  // Copyright (c) HashiCorp, Inc.
     2  // SPDX-License-Identifier: MPL-2.0
     3  
     4  package addrs
     5  
     6  // Set represents a set of addresses of types that implement UniqueKeyer.
     7  //
     8  // Modify the set only by the methods on this type. This type exposes its
     9  // internals for convenience during reading, such as iterating over set elements
    10  // by ranging over the map values, but making direct modifications could
    11  // potentially make the set data invalid or inconsistent, leading to undefined
    12  // behavior elsewhere.
    13  type Set[T UniqueKeyer] map[UniqueKey]T
    14  
    15  func MakeSet[T UniqueKeyer](elems ...T) Set[T] {
    16  	ret := Set[T](make(map[UniqueKey]T, len(elems)))
    17  	for _, elem := range elems {
    18  		ret.Add(elem)
    19  	}
    20  	return ret
    21  }
    22  
    23  // Has returns true if and only if the set includes the given address.
    24  func (s Set[T]) Has(addr T) bool {
    25  	_, exists := s[addr.UniqueKey()]
    26  	return exists
    27  }
    28  
    29  // Add inserts the given address into the set, if not already present. If
    30  // an equivalent address is already in the set, this replaces that address
    31  // with the new value.
    32  func (s Set[T]) Add(addr T) {
    33  	s[addr.UniqueKey()] = addr
    34  }
    35  
    36  // Remove deletes the given address from the set, if present. If not present,
    37  // this is a no-op.
    38  func (s Set[T]) Remove(addr T) {
    39  	delete(s, addr.UniqueKey())
    40  }
    41  
    42  // Union returns a new set which contains the union of all of the elements
    43  // of both the reciever and the given other set.
    44  func (s Set[T]) Union(other Set[T]) Set[T] {
    45  	ret := make(Set[T])
    46  	for k, addr := range s {
    47  		ret[k] = addr
    48  	}
    49  	for k, addr := range other {
    50  		ret[k] = addr
    51  	}
    52  	return ret
    53  }
    54  
    55  // Intersection returns a new set which contains the intersection of all of the
    56  // elements of both the reciever and the given other set.
    57  func (s Set[T]) Intersection(other Set[T]) Set[T] {
    58  	ret := make(Set[T])
    59  	for k, addr := range s {
    60  		if _, exists := other[k]; exists {
    61  			ret[k] = addr
    62  		}
    63  	}
    64  	for k, addr := range other {
    65  		if _, exists := s[k]; exists {
    66  			ret[k] = addr
    67  		}
    68  	}
    69  	return ret
    70  }