github.com/seeker-insurance/kit@v0.0.13/runeset/runeset.go (about)

     1  package runeset
     2  
     3  //RuneSet is a map[rune]bool with the methods you would expect from a set type.
     4  //Eg, Contains, Union, Intersection, and Difference.
     5  //I will make code generation for further set types in the future.
     6  type Signal struct{}
     7  
     8  var yes Signal
     9  
    10  type RuneSet map[rune]Signal
    11  
    12  //Contains shows whether r is in the RuneSet.
    13  func (rs RuneSet) Contains(r rune) bool {
    14  	_, ok := rs[r]
    15  	return ok
    16  }
    17  
    18  //Intersection returns the intersection of the sets;
    19  func (rs RuneSet) Intersection(sets ...RuneSet) (intersection RuneSet) {
    20  	intersection = rs.Copy()
    21  	for _, set := range sets {
    22  		for key := range intersection {
    23  			if _, ok := set[key]; !ok {
    24  				delete(intersection, key)
    25  			}
    26  		}
    27  	}
    28  	return intersection
    29  }
    30  
    31  func Intersection(set RuneSet, sets ...RuneSet) RuneSet {
    32  	return set.Intersection(sets...)
    33  }
    34  
    35  //Equal shows whether two RuneSets are equal; i.e, they contain the same items.
    36  func (rs RuneSet) Equal(other RuneSet) bool {
    37  	if len(rs) != len(other) {
    38  		return false
    39  	}
    40  	for r := range rs {
    41  		if !other.Contains(r) {
    42  			return false
    43  		}
    44  	}
    45  	return true
    46  }
    47  
    48  //Union returns the union of the sets.
    49  func (rs RuneSet) Union(sets ...RuneSet) (union RuneSet) {
    50  	sets = append(sets, rs)
    51  	return Union(sets...)
    52  }
    53  
    54  func Union(sets ...RuneSet) RuneSet {
    55  	union := make(RuneSet)
    56  	for _, set := range sets {
    57  		for r := range set {
    58  			union[r] = yes
    59  		}
    60  	}
    61  	return union
    62  }
    63  
    64  //Difference returns the items in the reciever but not any other arguments
    65  //i.e, if set = {'a', b' 'c'}; set.Difference({'b', 'c'}) = {'a'}
    66  func (rs RuneSet) Difference(sets ...RuneSet) (difference RuneSet) {
    67  	difference = rs.Copy()
    68  	for _, set := range sets {
    69  		for key := range difference {
    70  			if _, ok := set[key]; ok {
    71  				delete(difference, key)
    72  			}
    73  		}
    74  	}
    75  	return difference
    76  }
    77  
    78  //FromRunes creates a set from runes
    79  func FromRunes(runes ...rune) RuneSet {
    80  	set := make(RuneSet)
    81  	for _, r := range runes {
    82  		set[r] = yes
    83  	}
    84  	return set
    85  }
    86  
    87  //FromString converts a string to a RuneSet of the runes inside.
    88  func FromString(s string) (set RuneSet) {
    89  	set = make(RuneSet)
    90  	for _, r := range s {
    91  		set[r] = yes
    92  	}
    93  	return set
    94  }
    95  
    96  //Copy returns a copy of the RuneSet.
    97  func (rs RuneSet) Copy() RuneSet {
    98  	copy := make(RuneSet)
    99  	for k, v := range rs {
   100  		copy[k] = v
   101  	}
   102  	return copy
   103  }