forked from tangled.org/core
Monorepo for Tangled — https://tangled.org
at master 9.1 kB view raw
1package sets 2 3import ( 4 "slices" 5 "testing" 6 "testing/quick" 7) 8 9func TestNew(t *testing.T) { 10 s := New[int]() 11 if s.Len() != 0 { 12 t.Errorf("New set should be empty, got length %d", s.Len()) 13 } 14 if !s.IsEmpty() { 15 t.Error("New set should be empty") 16 } 17} 18 19func TestFromSlice(t *testing.T) { 20 s := Collect(slices.Values([]int{1, 2, 3, 2, 1})) 21 if s.Len() != 3 { 22 t.Errorf("Expected length 3, got %d", s.Len()) 23 } 24 if !s.Contains(1) || !s.Contains(2) || !s.Contains(3) { 25 t.Error("Set should contain all unique elements from slice") 26 } 27} 28 29func TestInsert(t *testing.T) { 30 s := New[string]() 31 32 if !s.Insert("hello") { 33 t.Error("First insert should return true") 34 } 35 if s.Insert("hello") { 36 t.Error("Duplicate insert should return false") 37 } 38 if s.Len() != 1 { 39 t.Errorf("Expected length 1, got %d", s.Len()) 40 } 41} 42 43func TestRemove(t *testing.T) { 44 s := Collect(slices.Values([]int{1, 2, 3})) 45 46 if !s.Remove(2) { 47 t.Error("Remove existing element should return true") 48 } 49 if s.Remove(2) { 50 t.Error("Remove non-existing element should return false") 51 } 52 if s.Contains(2) { 53 t.Error("Element should be removed") 54 } 55 if s.Len() != 2 { 56 t.Errorf("Expected length 2, got %d", s.Len()) 57 } 58} 59 60func TestContains(t *testing.T) { 61 s := Collect(slices.Values([]int{1, 2, 3})) 62 63 if !s.Contains(1) { 64 t.Error("Should contain 1") 65 } 66 if s.Contains(4) { 67 t.Error("Should not contain 4") 68 } 69} 70 71func TestClear(t *testing.T) { 72 s := Collect(slices.Values([]int{1, 2, 3})) 73 s.Clear() 74 75 if !s.IsEmpty() { 76 t.Error("Set should be empty after clear") 77 } 78 if s.Len() != 0 { 79 t.Errorf("Expected length 0, got %d", s.Len()) 80 } 81} 82 83func TestIterator(t *testing.T) { 84 s := Collect(slices.Values([]int{1, 2, 3})) 85 var items []int 86 87 for item := range s.All() { 88 items = append(items, item) 89 } 90 91 slices.Sort(items) 92 expected := []int{1, 2, 3} 93 if !slices.Equal(items, expected) { 94 t.Errorf("Expected %v, got %v", expected, items) 95 } 96} 97 98func TestClone(t *testing.T) { 99 s1 := Collect(slices.Values([]int{1, 2, 3})) 100 s2 := s1.Clone() 101 102 if !s1.Equal(s2) { 103 t.Error("Cloned set should be equal to original") 104 } 105 106 s2.Insert(4) 107 if s1.Contains(4) { 108 t.Error("Modifying clone should not affect original") 109 } 110} 111 112func TestUnion(t *testing.T) { 113 s1 := Collect(slices.Values([]int{1, 2})) 114 s2 := Collect(slices.Values([]int{2, 3})) 115 116 result := Collect(s1.Union(s2)) 117 expected := Collect(slices.Values([]int{1, 2, 3})) 118 119 if !result.Equal(expected) { 120 t.Errorf("Expected %v, got %v", expected, result) 121 } 122} 123 124func TestIntersection(t *testing.T) { 125 s1 := Collect(slices.Values([]int{1, 2, 3})) 126 s2 := Collect(slices.Values([]int{2, 3, 4})) 127 128 expected := Collect(slices.Values([]int{2, 3})) 129 result := Collect(s1.Intersection(s2)) 130 131 if !result.Equal(expected) { 132 t.Errorf("Expected %v, got %v", expected, result) 133 } 134} 135 136func TestDifference(t *testing.T) { 137 s1 := Collect(slices.Values([]int{1, 2, 3})) 138 s2 := Collect(slices.Values([]int{2, 3, 4})) 139 140 expected := Collect(slices.Values([]int{1})) 141 result := Collect(s1.Difference(s2)) 142 143 if !result.Equal(expected) { 144 t.Errorf("Expected %v, got %v", expected, result) 145 } 146} 147 148func TestSymmetricDifference(t *testing.T) { 149 s1 := Collect(slices.Values([]int{1, 2, 3})) 150 s2 := Collect(slices.Values([]int{2, 3, 4})) 151 152 expected := Collect(slices.Values([]int{1, 4})) 153 result := Collect(s1.SymmetricDifference(s2)) 154 155 if !result.Equal(expected) { 156 t.Errorf("Expected %v, got %v", expected, result) 157 } 158} 159 160func TestSymmetricDifferenceCommutativeProperty(t *testing.T) { 161 s1 := Collect(slices.Values([]int{1, 2, 3})) 162 s2 := Collect(slices.Values([]int{2, 3, 4})) 163 164 result1 := Collect(s1.SymmetricDifference(s2)) 165 result2 := Collect(s2.SymmetricDifference(s1)) 166 167 if !result1.Equal(result2) { 168 t.Errorf("Expected %v, got %v", result1, result2) 169 } 170} 171 172func TestIsSubset(t *testing.T) { 173 s1 := Collect(slices.Values([]int{1, 2})) 174 s2 := Collect(slices.Values([]int{1, 2, 3})) 175 176 if !s1.IsSubset(s2) { 177 t.Error("s1 should be subset of s2") 178 } 179 if s2.IsSubset(s1) { 180 t.Error("s2 should not be subset of s1") 181 } 182} 183 184func TestIsSuperset(t *testing.T) { 185 s1 := Collect(slices.Values([]int{1, 2, 3})) 186 s2 := Collect(slices.Values([]int{1, 2})) 187 188 if !s1.IsSuperset(s2) { 189 t.Error("s1 should be superset of s2") 190 } 191 if s2.IsSuperset(s1) { 192 t.Error("s2 should not be superset of s1") 193 } 194} 195 196func TestIsDisjoint(t *testing.T) { 197 s1 := Collect(slices.Values([]int{1, 2})) 198 s2 := Collect(slices.Values([]int{3, 4})) 199 s3 := Collect(slices.Values([]int{2, 3})) 200 201 if !s1.IsDisjoint(s2) { 202 t.Error("s1 and s2 should be disjoint") 203 } 204 if s1.IsDisjoint(s3) { 205 t.Error("s1 and s3 should not be disjoint") 206 } 207} 208 209func TestEqual(t *testing.T) { 210 s1 := Collect(slices.Values([]int{1, 2, 3})) 211 s2 := Collect(slices.Values([]int{3, 2, 1})) 212 s3 := Collect(slices.Values([]int{1, 2})) 213 214 if !s1.Equal(s2) { 215 t.Error("s1 and s2 should be equal") 216 } 217 if s1.Equal(s3) { 218 t.Error("s1 and s3 should not be equal") 219 } 220} 221 222func TestCollect(t *testing.T) { 223 s1 := Collect(slices.Values([]int{1, 2})) 224 s2 := Collect(slices.Values([]int{2, 3})) 225 226 unionSet := Collect(s1.Union(s2)) 227 if unionSet.Len() != 3 { 228 t.Errorf("Expected union set length 3, got %d", unionSet.Len()) 229 } 230 if !unionSet.Contains(1) || !unionSet.Contains(2) || !unionSet.Contains(3) { 231 t.Error("Union set should contain 1, 2, and 3") 232 } 233 234 diffSet := Collect(s1.Difference(s2)) 235 if diffSet.Len() != 1 { 236 t.Errorf("Expected difference set length 1, got %d", diffSet.Len()) 237 } 238 if !diffSet.Contains(1) { 239 t.Error("Difference set should contain 1") 240 } 241} 242 243func TestPropertySingleonLen(t *testing.T) { 244 f := func(item int) bool { 245 single := Singleton(item) 246 return single.Len() == 1 247 } 248 249 if err := quick.Check(f, nil); err != nil { 250 t.Error(err) 251 } 252} 253 254func TestPropertyInsertIdempotent(t *testing.T) { 255 f := func(s Set[int], item int) bool { 256 clone := s.Clone() 257 258 clone.Insert(item) 259 firstLen := clone.Len() 260 261 clone.Insert(item) 262 secondLen := clone.Len() 263 264 return firstLen == secondLen 265 } 266 267 if err := quick.Check(f, nil); err != nil { 268 t.Error(err) 269 } 270} 271 272func TestPropertyUnionCommutative(t *testing.T) { 273 f := func(s1 Set[int], s2 Set[int]) bool { 274 union1 := Collect(s1.Union(s2)) 275 union2 := Collect(s2.Union(s1)) 276 return union1.Equal(union2) 277 } 278 279 if err := quick.Check(f, nil); err != nil { 280 t.Error(err) 281 } 282} 283 284func TestPropertyIntersectionCommutative(t *testing.T) { 285 f := func(s1 Set[int], s2 Set[int]) bool { 286 inter1 := Collect(s1.Intersection(s2)) 287 inter2 := Collect(s2.Intersection(s1)) 288 return inter1.Equal(inter2) 289 } 290 291 if err := quick.Check(f, nil); err != nil { 292 t.Error(err) 293 } 294} 295 296func TestPropertyCloneEquals(t *testing.T) { 297 f := func(s Set[int]) bool { 298 clone := s.Clone() 299 return s.Equal(clone) 300 } 301 302 if err := quick.Check(f, nil); err != nil { 303 t.Error(err) 304 } 305} 306 307func TestPropertyIntersectionIsSubset(t *testing.T) { 308 f := func(s1 Set[int], s2 Set[int]) bool { 309 inter := Collect(s1.Intersection(s2)) 310 return inter.IsSubset(s1) && inter.IsSubset(s2) 311 } 312 313 if err := quick.Check(f, nil); err != nil { 314 t.Error(err) 315 } 316} 317 318func TestPropertyUnionIsSuperset(t *testing.T) { 319 f := func(s1 Set[int], s2 Set[int]) bool { 320 union := Collect(s1.Union(s2)) 321 return union.IsSuperset(s1) && union.IsSuperset(s2) 322 } 323 324 if err := quick.Check(f, nil); err != nil { 325 t.Error(err) 326 } 327} 328 329func TestPropertyDifferenceDisjoint(t *testing.T) { 330 f := func(s1 Set[int], s2 Set[int]) bool { 331 diff := Collect(s1.Difference(s2)) 332 return diff.IsDisjoint(s2) 333 } 334 335 if err := quick.Check(f, nil); err != nil { 336 t.Error(err) 337 } 338} 339 340func TestPropertySymmetricDifferenceCommutative(t *testing.T) { 341 f := func(s1 Set[int], s2 Set[int]) bool { 342 symDiff1 := Collect(s1.SymmetricDifference(s2)) 343 symDiff2 := Collect(s2.SymmetricDifference(s1)) 344 return symDiff1.Equal(symDiff2) 345 } 346 347 if err := quick.Check(f, nil); err != nil { 348 t.Error(err) 349 } 350} 351 352func TestPropertyRemoveWorks(t *testing.T) { 353 f := func(s Set[int], item int) bool { 354 clone := s.Clone() 355 clone.Insert(item) 356 clone.Remove(item) 357 return !clone.Contains(item) 358 } 359 360 if err := quick.Check(f, nil); err != nil { 361 t.Error(err) 362 } 363} 364 365func TestPropertyClearEmpty(t *testing.T) { 366 f := func(s Set[int]) bool { 367 s.Clear() 368 return s.IsEmpty() && s.Len() == 0 369 } 370 371 if err := quick.Check(f, nil); err != nil { 372 t.Error(err) 373 } 374} 375 376func TestPropertyIsSubsetReflexive(t *testing.T) { 377 f := func(s Set[int]) bool { 378 return s.IsSubset(s) 379 } 380 381 if err := quick.Check(f, nil); err != nil { 382 t.Error(err) 383 } 384} 385 386func TestPropertyDeMorganUnion(t *testing.T) { 387 f := func(s1 Set[int], s2 Set[int], universe Set[int]) bool { 388 // create a universe that contains both sets 389 u := universe.Clone() 390 for item := range s1.All() { 391 u.Insert(item) 392 } 393 for item := range s2.All() { 394 u.Insert(item) 395 } 396 397 // (A u B)' = A' n B' 398 union := Collect(s1.Union(s2)) 399 complementUnion := Collect(u.Difference(union)) 400 401 complementS1 := Collect(u.Difference(s1)) 402 complementS2 := Collect(u.Difference(s2)) 403 intersectionComplements := Collect(complementS1.Intersection(complementS2)) 404 405 return complementUnion.Equal(intersectionComplements) 406 } 407 408 if err := quick.Check(f, nil); err != nil { 409 t.Error(err) 410 } 411}