1 | #!/usr/bin/env python
|
---|
2 |
|
---|
3 | import unittest, operator, copy, pickle, random
|
---|
4 | from test import test_support
|
---|
5 |
|
---|
6 | test_support.import_module("sets", deprecated=True)
|
---|
7 | from sets import Set, ImmutableSet
|
---|
8 |
|
---|
9 | empty_set = Set()
|
---|
10 |
|
---|
11 | #==============================================================================
|
---|
12 |
|
---|
13 | class TestBasicOps(unittest.TestCase):
|
---|
14 |
|
---|
15 | def test_repr(self):
|
---|
16 | if self.repr is not None:
|
---|
17 | self.assertEqual(repr(self.set), self.repr)
|
---|
18 |
|
---|
19 | def test_length(self):
|
---|
20 | self.assertEqual(len(self.set), self.length)
|
---|
21 |
|
---|
22 | def test_self_equality(self):
|
---|
23 | self.assertEqual(self.set, self.set)
|
---|
24 |
|
---|
25 | def test_equivalent_equality(self):
|
---|
26 | self.assertEqual(self.set, self.dup)
|
---|
27 |
|
---|
28 | def test_copy(self):
|
---|
29 | self.assertEqual(self.set.copy(), self.dup)
|
---|
30 |
|
---|
31 | def test_self_union(self):
|
---|
32 | result = self.set | self.set
|
---|
33 | self.assertEqual(result, self.dup)
|
---|
34 |
|
---|
35 | def test_empty_union(self):
|
---|
36 | result = self.set | empty_set
|
---|
37 | self.assertEqual(result, self.dup)
|
---|
38 |
|
---|
39 | def test_union_empty(self):
|
---|
40 | result = empty_set | self.set
|
---|
41 | self.assertEqual(result, self.dup)
|
---|
42 |
|
---|
43 | def test_self_intersection(self):
|
---|
44 | result = self.set & self.set
|
---|
45 | self.assertEqual(result, self.dup)
|
---|
46 |
|
---|
47 | def test_empty_intersection(self):
|
---|
48 | result = self.set & empty_set
|
---|
49 | self.assertEqual(result, empty_set)
|
---|
50 |
|
---|
51 | def test_intersection_empty(self):
|
---|
52 | result = empty_set & self.set
|
---|
53 | self.assertEqual(result, empty_set)
|
---|
54 |
|
---|
55 | def test_self_symmetric_difference(self):
|
---|
56 | result = self.set ^ self.set
|
---|
57 | self.assertEqual(result, empty_set)
|
---|
58 |
|
---|
59 | def checkempty_symmetric_difference(self):
|
---|
60 | result = self.set ^ empty_set
|
---|
61 | self.assertEqual(result, self.set)
|
---|
62 |
|
---|
63 | def test_self_difference(self):
|
---|
64 | result = self.set - self.set
|
---|
65 | self.assertEqual(result, empty_set)
|
---|
66 |
|
---|
67 | def test_empty_difference(self):
|
---|
68 | result = self.set - empty_set
|
---|
69 | self.assertEqual(result, self.dup)
|
---|
70 |
|
---|
71 | def test_empty_difference_rev(self):
|
---|
72 | result = empty_set - self.set
|
---|
73 | self.assertEqual(result, empty_set)
|
---|
74 |
|
---|
75 | def test_iteration(self):
|
---|
76 | for v in self.set:
|
---|
77 | self.assertIn(v, self.values)
|
---|
78 |
|
---|
79 | def test_pickling(self):
|
---|
80 | p = pickle.dumps(self.set)
|
---|
81 | copy = pickle.loads(p)
|
---|
82 | self.assertEqual(self.set, copy,
|
---|
83 | "%s != %s" % (self.set, copy))
|
---|
84 |
|
---|
85 | #------------------------------------------------------------------------------
|
---|
86 |
|
---|
87 | class TestBasicOpsEmpty(TestBasicOps):
|
---|
88 | def setUp(self):
|
---|
89 | self.case = "empty set"
|
---|
90 | self.values = []
|
---|
91 | self.set = Set(self.values)
|
---|
92 | self.dup = Set(self.values)
|
---|
93 | self.length = 0
|
---|
94 | self.repr = "Set([])"
|
---|
95 |
|
---|
96 | #------------------------------------------------------------------------------
|
---|
97 |
|
---|
98 | class TestBasicOpsSingleton(TestBasicOps):
|
---|
99 | def setUp(self):
|
---|
100 | self.case = "unit set (number)"
|
---|
101 | self.values = [3]
|
---|
102 | self.set = Set(self.values)
|
---|
103 | self.dup = Set(self.values)
|
---|
104 | self.length = 1
|
---|
105 | self.repr = "Set([3])"
|
---|
106 |
|
---|
107 | def test_in(self):
|
---|
108 | self.assertTrue(3 in self.set)
|
---|
109 |
|
---|
110 | def test_not_in(self):
|
---|
111 | self.assertTrue(2 not in self.set)
|
---|
112 |
|
---|
113 | #------------------------------------------------------------------------------
|
---|
114 |
|
---|
115 | class TestBasicOpsTuple(TestBasicOps):
|
---|
116 | def setUp(self):
|
---|
117 | self.case = "unit set (tuple)"
|
---|
118 | self.values = [(0, "zero")]
|
---|
119 | self.set = Set(self.values)
|
---|
120 | self.dup = Set(self.values)
|
---|
121 | self.length = 1
|
---|
122 | self.repr = "Set([(0, 'zero')])"
|
---|
123 |
|
---|
124 | def test_in(self):
|
---|
125 | self.assertTrue((0, "zero") in self.set)
|
---|
126 |
|
---|
127 | def test_not_in(self):
|
---|
128 | self.assertTrue(9 not in self.set)
|
---|
129 |
|
---|
130 | #------------------------------------------------------------------------------
|
---|
131 |
|
---|
132 | class TestBasicOpsTriple(TestBasicOps):
|
---|
133 | def setUp(self):
|
---|
134 | self.case = "triple set"
|
---|
135 | self.values = [0, "zero", operator.add]
|
---|
136 | self.set = Set(self.values)
|
---|
137 | self.dup = Set(self.values)
|
---|
138 | self.length = 3
|
---|
139 | self.repr = None
|
---|
140 |
|
---|
141 | #==============================================================================
|
---|
142 |
|
---|
143 | def baditer():
|
---|
144 | raise TypeError
|
---|
145 | yield True
|
---|
146 |
|
---|
147 | def gooditer():
|
---|
148 | yield True
|
---|
149 |
|
---|
150 | class TestExceptionPropagation(unittest.TestCase):
|
---|
151 | """SF 628246: Set constructor should not trap iterator TypeErrors"""
|
---|
152 |
|
---|
153 | def test_instanceWithException(self):
|
---|
154 | self.assertRaises(TypeError, Set, baditer())
|
---|
155 |
|
---|
156 | def test_instancesWithoutException(self):
|
---|
157 | # All of these iterables should load without exception.
|
---|
158 | Set([1,2,3])
|
---|
159 | Set((1,2,3))
|
---|
160 | Set({'one':1, 'two':2, 'three':3})
|
---|
161 | Set(xrange(3))
|
---|
162 | Set('abc')
|
---|
163 | Set(gooditer())
|
---|
164 |
|
---|
165 | #==============================================================================
|
---|
166 |
|
---|
167 | class TestSetOfSets(unittest.TestCase):
|
---|
168 | def test_constructor(self):
|
---|
169 | inner = Set([1])
|
---|
170 | outer = Set([inner])
|
---|
171 | element = outer.pop()
|
---|
172 | self.assertEqual(type(element), ImmutableSet)
|
---|
173 | outer.add(inner) # Rebuild set of sets with .add method
|
---|
174 | outer.remove(inner)
|
---|
175 | self.assertEqual(outer, Set()) # Verify that remove worked
|
---|
176 | outer.discard(inner) # Absence of KeyError indicates working fine
|
---|
177 |
|
---|
178 | #==============================================================================
|
---|
179 |
|
---|
180 | class TestBinaryOps(unittest.TestCase):
|
---|
181 | def setUp(self):
|
---|
182 | self.set = Set((2, 4, 6))
|
---|
183 |
|
---|
184 | def test_eq(self): # SF bug 643115
|
---|
185 | self.assertEqual(self.set, Set({2:1,4:3,6:5}))
|
---|
186 |
|
---|
187 | def test_union_subset(self):
|
---|
188 | result = self.set | Set([2])
|
---|
189 | self.assertEqual(result, Set((2, 4, 6)))
|
---|
190 |
|
---|
191 | def test_union_superset(self):
|
---|
192 | result = self.set | Set([2, 4, 6, 8])
|
---|
193 | self.assertEqual(result, Set([2, 4, 6, 8]))
|
---|
194 |
|
---|
195 | def test_union_overlap(self):
|
---|
196 | result = self.set | Set([3, 4, 5])
|
---|
197 | self.assertEqual(result, Set([2, 3, 4, 5, 6]))
|
---|
198 |
|
---|
199 | def test_union_non_overlap(self):
|
---|
200 | result = self.set | Set([8])
|
---|
201 | self.assertEqual(result, Set([2, 4, 6, 8]))
|
---|
202 |
|
---|
203 | def test_intersection_subset(self):
|
---|
204 | result = self.set & Set((2, 4))
|
---|
205 | self.assertEqual(result, Set((2, 4)))
|
---|
206 |
|
---|
207 | def test_intersection_superset(self):
|
---|
208 | result = self.set & Set([2, 4, 6, 8])
|
---|
209 | self.assertEqual(result, Set([2, 4, 6]))
|
---|
210 |
|
---|
211 | def test_intersection_overlap(self):
|
---|
212 | result = self.set & Set([3, 4, 5])
|
---|
213 | self.assertEqual(result, Set([4]))
|
---|
214 |
|
---|
215 | def test_intersection_non_overlap(self):
|
---|
216 | result = self.set & Set([8])
|
---|
217 | self.assertEqual(result, empty_set)
|
---|
218 |
|
---|
219 | def test_sym_difference_subset(self):
|
---|
220 | result = self.set ^ Set((2, 4))
|
---|
221 | self.assertEqual(result, Set([6]))
|
---|
222 |
|
---|
223 | def test_sym_difference_superset(self):
|
---|
224 | result = self.set ^ Set((2, 4, 6, 8))
|
---|
225 | self.assertEqual(result, Set([8]))
|
---|
226 |
|
---|
227 | def test_sym_difference_overlap(self):
|
---|
228 | result = self.set ^ Set((3, 4, 5))
|
---|
229 | self.assertEqual(result, Set([2, 3, 5, 6]))
|
---|
230 |
|
---|
231 | def test_sym_difference_non_overlap(self):
|
---|
232 | result = self.set ^ Set([8])
|
---|
233 | self.assertEqual(result, Set([2, 4, 6, 8]))
|
---|
234 |
|
---|
235 | def test_cmp(self):
|
---|
236 | a, b = Set('a'), Set('b')
|
---|
237 | self.assertRaises(TypeError, cmp, a, b)
|
---|
238 |
|
---|
239 | # You can view this as a buglet: cmp(a, a) does not raise TypeError,
|
---|
240 | # because __eq__ is tried before __cmp__, and a.__eq__(a) returns True,
|
---|
241 | # which Python thinks is good enough to synthesize a cmp() result
|
---|
242 | # without calling __cmp__.
|
---|
243 | self.assertEqual(cmp(a, a), 0)
|
---|
244 |
|
---|
245 | self.assertRaises(TypeError, cmp, a, 12)
|
---|
246 | self.assertRaises(TypeError, cmp, "abc", a)
|
---|
247 |
|
---|
248 | def test_inplace_on_self(self):
|
---|
249 | t = self.set.copy()
|
---|
250 | t |= t
|
---|
251 | self.assertEqual(t, self.set)
|
---|
252 | t &= t
|
---|
253 | self.assertEqual(t, self.set)
|
---|
254 | t -= t
|
---|
255 | self.assertEqual(len(t), 0)
|
---|
256 | t = self.set.copy()
|
---|
257 | t ^= t
|
---|
258 | self.assertEqual(len(t), 0)
|
---|
259 |
|
---|
260 |
|
---|
261 | #==============================================================================
|
---|
262 |
|
---|
263 | class TestUpdateOps(unittest.TestCase):
|
---|
264 | def setUp(self):
|
---|
265 | self.set = Set((2, 4, 6))
|
---|
266 |
|
---|
267 | def test_union_subset(self):
|
---|
268 | self.set |= Set([2])
|
---|
269 | self.assertEqual(self.set, Set((2, 4, 6)))
|
---|
270 |
|
---|
271 | def test_union_superset(self):
|
---|
272 | self.set |= Set([2, 4, 6, 8])
|
---|
273 | self.assertEqual(self.set, Set([2, 4, 6, 8]))
|
---|
274 |
|
---|
275 | def test_union_overlap(self):
|
---|
276 | self.set |= Set([3, 4, 5])
|
---|
277 | self.assertEqual(self.set, Set([2, 3, 4, 5, 6]))
|
---|
278 |
|
---|
279 | def test_union_non_overlap(self):
|
---|
280 | self.set |= Set([8])
|
---|
281 | self.assertEqual(self.set, Set([2, 4, 6, 8]))
|
---|
282 |
|
---|
283 | def test_union_method_call(self):
|
---|
284 | self.set.union_update(Set([3, 4, 5]))
|
---|
285 | self.assertEqual(self.set, Set([2, 3, 4, 5, 6]))
|
---|
286 |
|
---|
287 | def test_intersection_subset(self):
|
---|
288 | self.set &= Set((2, 4))
|
---|
289 | self.assertEqual(self.set, Set((2, 4)))
|
---|
290 |
|
---|
291 | def test_intersection_superset(self):
|
---|
292 | self.set &= Set([2, 4, 6, 8])
|
---|
293 | self.assertEqual(self.set, Set([2, 4, 6]))
|
---|
294 |
|
---|
295 | def test_intersection_overlap(self):
|
---|
296 | self.set &= Set([3, 4, 5])
|
---|
297 | self.assertEqual(self.set, Set([4]))
|
---|
298 |
|
---|
299 | def test_intersection_non_overlap(self):
|
---|
300 | self.set &= Set([8])
|
---|
301 | self.assertEqual(self.set, empty_set)
|
---|
302 |
|
---|
303 | def test_intersection_method_call(self):
|
---|
304 | self.set.intersection_update(Set([3, 4, 5]))
|
---|
305 | self.assertEqual(self.set, Set([4]))
|
---|
306 |
|
---|
307 | def test_sym_difference_subset(self):
|
---|
308 | self.set ^= Set((2, 4))
|
---|
309 | self.assertEqual(self.set, Set([6]))
|
---|
310 |
|
---|
311 | def test_sym_difference_superset(self):
|
---|
312 | self.set ^= Set((2, 4, 6, 8))
|
---|
313 | self.assertEqual(self.set, Set([8]))
|
---|
314 |
|
---|
315 | def test_sym_difference_overlap(self):
|
---|
316 | self.set ^= Set((3, 4, 5))
|
---|
317 | self.assertEqual(self.set, Set([2, 3, 5, 6]))
|
---|
318 |
|
---|
319 | def test_sym_difference_non_overlap(self):
|
---|
320 | self.set ^= Set([8])
|
---|
321 | self.assertEqual(self.set, Set([2, 4, 6, 8]))
|
---|
322 |
|
---|
323 | def test_sym_difference_method_call(self):
|
---|
324 | self.set.symmetric_difference_update(Set([3, 4, 5]))
|
---|
325 | self.assertEqual(self.set, Set([2, 3, 5, 6]))
|
---|
326 |
|
---|
327 | def test_difference_subset(self):
|
---|
328 | self.set -= Set((2, 4))
|
---|
329 | self.assertEqual(self.set, Set([6]))
|
---|
330 |
|
---|
331 | def test_difference_superset(self):
|
---|
332 | self.set -= Set((2, 4, 6, 8))
|
---|
333 | self.assertEqual(self.set, Set([]))
|
---|
334 |
|
---|
335 | def test_difference_overlap(self):
|
---|
336 | self.set -= Set((3, 4, 5))
|
---|
337 | self.assertEqual(self.set, Set([2, 6]))
|
---|
338 |
|
---|
339 | def test_difference_non_overlap(self):
|
---|
340 | self.set -= Set([8])
|
---|
341 | self.assertEqual(self.set, Set([2, 4, 6]))
|
---|
342 |
|
---|
343 | def test_difference_method_call(self):
|
---|
344 | self.set.difference_update(Set([3, 4, 5]))
|
---|
345 | self.assertEqual(self.set, Set([2, 6]))
|
---|
346 |
|
---|
347 | #==============================================================================
|
---|
348 |
|
---|
349 | class TestMutate(unittest.TestCase):
|
---|
350 | def setUp(self):
|
---|
351 | self.values = ["a", "b", "c"]
|
---|
352 | self.set = Set(self.values)
|
---|
353 |
|
---|
354 | def test_add_present(self):
|
---|
355 | self.set.add("c")
|
---|
356 | self.assertEqual(self.set, Set("abc"))
|
---|
357 |
|
---|
358 | def test_add_absent(self):
|
---|
359 | self.set.add("d")
|
---|
360 | self.assertEqual(self.set, Set("abcd"))
|
---|
361 |
|
---|
362 | def test_add_until_full(self):
|
---|
363 | tmp = Set()
|
---|
364 | expected_len = 0
|
---|
365 | for v in self.values:
|
---|
366 | tmp.add(v)
|
---|
367 | expected_len += 1
|
---|
368 | self.assertEqual(len(tmp), expected_len)
|
---|
369 | self.assertEqual(tmp, self.set)
|
---|
370 |
|
---|
371 | def test_remove_present(self):
|
---|
372 | self.set.remove("b")
|
---|
373 | self.assertEqual(self.set, Set("ac"))
|
---|
374 |
|
---|
375 | def test_remove_absent(self):
|
---|
376 | try:
|
---|
377 | self.set.remove("d")
|
---|
378 | self.fail("Removing missing element should have raised LookupError")
|
---|
379 | except LookupError:
|
---|
380 | pass
|
---|
381 |
|
---|
382 | def test_remove_until_empty(self):
|
---|
383 | expected_len = len(self.set)
|
---|
384 | for v in self.values:
|
---|
385 | self.set.remove(v)
|
---|
386 | expected_len -= 1
|
---|
387 | self.assertEqual(len(self.set), expected_len)
|
---|
388 |
|
---|
389 | def test_discard_present(self):
|
---|
390 | self.set.discard("c")
|
---|
391 | self.assertEqual(self.set, Set("ab"))
|
---|
392 |
|
---|
393 | def test_discard_absent(self):
|
---|
394 | self.set.discard("d")
|
---|
395 | self.assertEqual(self.set, Set("abc"))
|
---|
396 |
|
---|
397 | def test_clear(self):
|
---|
398 | self.set.clear()
|
---|
399 | self.assertEqual(len(self.set), 0)
|
---|
400 |
|
---|
401 | def test_pop(self):
|
---|
402 | popped = {}
|
---|
403 | while self.set:
|
---|
404 | popped[self.set.pop()] = None
|
---|
405 | self.assertEqual(len(popped), len(self.values))
|
---|
406 | for v in self.values:
|
---|
407 | self.assertIn(v, popped)
|
---|
408 |
|
---|
409 | def test_update_empty_tuple(self):
|
---|
410 | self.set.union_update(())
|
---|
411 | self.assertEqual(self.set, Set(self.values))
|
---|
412 |
|
---|
413 | def test_update_unit_tuple_overlap(self):
|
---|
414 | self.set.union_update(("a",))
|
---|
415 | self.assertEqual(self.set, Set(self.values))
|
---|
416 |
|
---|
417 | def test_update_unit_tuple_non_overlap(self):
|
---|
418 | self.set.union_update(("a", "z"))
|
---|
419 | self.assertEqual(self.set, Set(self.values + ["z"]))
|
---|
420 |
|
---|
421 | #==============================================================================
|
---|
422 |
|
---|
423 | class TestSubsets(unittest.TestCase):
|
---|
424 |
|
---|
425 | case2method = {"<=": "issubset",
|
---|
426 | ">=": "issuperset",
|
---|
427 | }
|
---|
428 |
|
---|
429 | reverse = {"==": "==",
|
---|
430 | "!=": "!=",
|
---|
431 | "<": ">",
|
---|
432 | ">": "<",
|
---|
433 | "<=": ">=",
|
---|
434 | ">=": "<=",
|
---|
435 | }
|
---|
436 |
|
---|
437 | def test_issubset(self):
|
---|
438 | x = self.left
|
---|
439 | y = self.right
|
---|
440 | for case in "!=", "==", "<", "<=", ">", ">=":
|
---|
441 | expected = case in self.cases
|
---|
442 | # Test the binary infix spelling.
|
---|
443 | result = eval("x" + case + "y", locals())
|
---|
444 | self.assertEqual(result, expected)
|
---|
445 | # Test the "friendly" method-name spelling, if one exists.
|
---|
446 | if case in TestSubsets.case2method:
|
---|
447 | method = getattr(x, TestSubsets.case2method[case])
|
---|
448 | result = method(y)
|
---|
449 | self.assertEqual(result, expected)
|
---|
450 |
|
---|
451 | # Now do the same for the operands reversed.
|
---|
452 | rcase = TestSubsets.reverse[case]
|
---|
453 | result = eval("y" + rcase + "x", locals())
|
---|
454 | self.assertEqual(result, expected)
|
---|
455 | if rcase in TestSubsets.case2method:
|
---|
456 | method = getattr(y, TestSubsets.case2method[rcase])
|
---|
457 | result = method(x)
|
---|
458 | self.assertEqual(result, expected)
|
---|
459 | #------------------------------------------------------------------------------
|
---|
460 |
|
---|
461 | class TestSubsetEqualEmpty(TestSubsets):
|
---|
462 | left = Set()
|
---|
463 | right = Set()
|
---|
464 | name = "both empty"
|
---|
465 | cases = "==", "<=", ">="
|
---|
466 |
|
---|
467 | #------------------------------------------------------------------------------
|
---|
468 |
|
---|
469 | class TestSubsetEqualNonEmpty(TestSubsets):
|
---|
470 | left = Set([1, 2])
|
---|
471 | right = Set([1, 2])
|
---|
472 | name = "equal pair"
|
---|
473 | cases = "==", "<=", ">="
|
---|
474 |
|
---|
475 | #------------------------------------------------------------------------------
|
---|
476 |
|
---|
477 | class TestSubsetEmptyNonEmpty(TestSubsets):
|
---|
478 | left = Set()
|
---|
479 | right = Set([1, 2])
|
---|
480 | name = "one empty, one non-empty"
|
---|
481 | cases = "!=", "<", "<="
|
---|
482 |
|
---|
483 | #------------------------------------------------------------------------------
|
---|
484 |
|
---|
485 | class TestSubsetPartial(TestSubsets):
|
---|
486 | left = Set([1])
|
---|
487 | right = Set([1, 2])
|
---|
488 | name = "one a non-empty proper subset of other"
|
---|
489 | cases = "!=", "<", "<="
|
---|
490 |
|
---|
491 | #------------------------------------------------------------------------------
|
---|
492 |
|
---|
493 | class TestSubsetNonOverlap(TestSubsets):
|
---|
494 | left = Set([1])
|
---|
495 | right = Set([2])
|
---|
496 | name = "neither empty, neither contains"
|
---|
497 | cases = "!="
|
---|
498 |
|
---|
499 | #==============================================================================
|
---|
500 |
|
---|
501 | class TestOnlySetsInBinaryOps(unittest.TestCase):
|
---|
502 |
|
---|
503 | def test_eq_ne(self):
|
---|
504 | # Unlike the others, this is testing that == and != *are* allowed.
|
---|
505 | self.assertEqual(self.other == self.set, False)
|
---|
506 | self.assertEqual(self.set == self.other, False)
|
---|
507 | self.assertEqual(self.other != self.set, True)
|
---|
508 | self.assertEqual(self.set != self.other, True)
|
---|
509 |
|
---|
510 | def test_ge_gt_le_lt(self):
|
---|
511 | self.assertRaises(TypeError, lambda: self.set < self.other)
|
---|
512 | self.assertRaises(TypeError, lambda: self.set <= self.other)
|
---|
513 | self.assertRaises(TypeError, lambda: self.set > self.other)
|
---|
514 | self.assertRaises(TypeError, lambda: self.set >= self.other)
|
---|
515 |
|
---|
516 | self.assertRaises(TypeError, lambda: self.other < self.set)
|
---|
517 | self.assertRaises(TypeError, lambda: self.other <= self.set)
|
---|
518 | self.assertRaises(TypeError, lambda: self.other > self.set)
|
---|
519 | self.assertRaises(TypeError, lambda: self.other >= self.set)
|
---|
520 |
|
---|
521 | def test_union_update_operator(self):
|
---|
522 | try:
|
---|
523 | self.set |= self.other
|
---|
524 | except TypeError:
|
---|
525 | pass
|
---|
526 | else:
|
---|
527 | self.fail("expected TypeError")
|
---|
528 |
|
---|
529 | def test_union_update(self):
|
---|
530 | if self.otherIsIterable:
|
---|
531 | self.set.union_update(self.other)
|
---|
532 | else:
|
---|
533 | self.assertRaises(TypeError, self.set.union_update, self.other)
|
---|
534 |
|
---|
535 | def test_union(self):
|
---|
536 | self.assertRaises(TypeError, lambda: self.set | self.other)
|
---|
537 | self.assertRaises(TypeError, lambda: self.other | self.set)
|
---|
538 | if self.otherIsIterable:
|
---|
539 | self.set.union(self.other)
|
---|
540 | else:
|
---|
541 | self.assertRaises(TypeError, self.set.union, self.other)
|
---|
542 |
|
---|
543 | def test_intersection_update_operator(self):
|
---|
544 | try:
|
---|
545 | self.set &= self.other
|
---|
546 | except TypeError:
|
---|
547 | pass
|
---|
548 | else:
|
---|
549 | self.fail("expected TypeError")
|
---|
550 |
|
---|
551 | def test_intersection_update(self):
|
---|
552 | if self.otherIsIterable:
|
---|
553 | self.set.intersection_update(self.other)
|
---|
554 | else:
|
---|
555 | self.assertRaises(TypeError,
|
---|
556 | self.set.intersection_update,
|
---|
557 | self.other)
|
---|
558 |
|
---|
559 | def test_intersection(self):
|
---|
560 | self.assertRaises(TypeError, lambda: self.set & self.other)
|
---|
561 | self.assertRaises(TypeError, lambda: self.other & self.set)
|
---|
562 | if self.otherIsIterable:
|
---|
563 | self.set.intersection(self.other)
|
---|
564 | else:
|
---|
565 | self.assertRaises(TypeError, self.set.intersection, self.other)
|
---|
566 |
|
---|
567 | def test_sym_difference_update_operator(self):
|
---|
568 | try:
|
---|
569 | self.set ^= self.other
|
---|
570 | except TypeError:
|
---|
571 | pass
|
---|
572 | else:
|
---|
573 | self.fail("expected TypeError")
|
---|
574 |
|
---|
575 | def test_sym_difference_update(self):
|
---|
576 | if self.otherIsIterable:
|
---|
577 | self.set.symmetric_difference_update(self.other)
|
---|
578 | else:
|
---|
579 | self.assertRaises(TypeError,
|
---|
580 | self.set.symmetric_difference_update,
|
---|
581 | self.other)
|
---|
582 |
|
---|
583 | def test_sym_difference(self):
|
---|
584 | self.assertRaises(TypeError, lambda: self.set ^ self.other)
|
---|
585 | self.assertRaises(TypeError, lambda: self.other ^ self.set)
|
---|
586 | if self.otherIsIterable:
|
---|
587 | self.set.symmetric_difference(self.other)
|
---|
588 | else:
|
---|
589 | self.assertRaises(TypeError, self.set.symmetric_difference, self.other)
|
---|
590 |
|
---|
591 | def test_difference_update_operator(self):
|
---|
592 | try:
|
---|
593 | self.set -= self.other
|
---|
594 | except TypeError:
|
---|
595 | pass
|
---|
596 | else:
|
---|
597 | self.fail("expected TypeError")
|
---|
598 |
|
---|
599 | def test_difference_update(self):
|
---|
600 | if self.otherIsIterable:
|
---|
601 | self.set.difference_update(self.other)
|
---|
602 | else:
|
---|
603 | self.assertRaises(TypeError,
|
---|
604 | self.set.difference_update,
|
---|
605 | self.other)
|
---|
606 |
|
---|
607 | def test_difference(self):
|
---|
608 | self.assertRaises(TypeError, lambda: self.set - self.other)
|
---|
609 | self.assertRaises(TypeError, lambda: self.other - self.set)
|
---|
610 | if self.otherIsIterable:
|
---|
611 | self.set.difference(self.other)
|
---|
612 | else:
|
---|
613 | self.assertRaises(TypeError, self.set.difference, self.other)
|
---|
614 |
|
---|
615 | #------------------------------------------------------------------------------
|
---|
616 |
|
---|
617 | class TestOnlySetsNumeric(TestOnlySetsInBinaryOps):
|
---|
618 | def setUp(self):
|
---|
619 | self.set = Set((1, 2, 3))
|
---|
620 | self.other = 19
|
---|
621 | self.otherIsIterable = False
|
---|
622 |
|
---|
623 | #------------------------------------------------------------------------------
|
---|
624 |
|
---|
625 | class TestOnlySetsDict(TestOnlySetsInBinaryOps):
|
---|
626 | def setUp(self):
|
---|
627 | self.set = Set((1, 2, 3))
|
---|
628 | self.other = {1:2, 3:4}
|
---|
629 | self.otherIsIterable = True
|
---|
630 |
|
---|
631 | #------------------------------------------------------------------------------
|
---|
632 |
|
---|
633 | class TestOnlySetsOperator(TestOnlySetsInBinaryOps):
|
---|
634 | def setUp(self):
|
---|
635 | self.set = Set((1, 2, 3))
|
---|
636 | self.other = operator.add
|
---|
637 | self.otherIsIterable = False
|
---|
638 |
|
---|
639 | def test_ge_gt_le_lt(self):
|
---|
640 | with test_support.check_py3k_warnings():
|
---|
641 | super(TestOnlySetsOperator, self).test_ge_gt_le_lt()
|
---|
642 |
|
---|
643 | #------------------------------------------------------------------------------
|
---|
644 |
|
---|
645 | class TestOnlySetsTuple(TestOnlySetsInBinaryOps):
|
---|
646 | def setUp(self):
|
---|
647 | self.set = Set((1, 2, 3))
|
---|
648 | self.other = (2, 4, 6)
|
---|
649 | self.otherIsIterable = True
|
---|
650 |
|
---|
651 | #------------------------------------------------------------------------------
|
---|
652 |
|
---|
653 | class TestOnlySetsString(TestOnlySetsInBinaryOps):
|
---|
654 | def setUp(self):
|
---|
655 | self.set = Set((1, 2, 3))
|
---|
656 | self.other = 'abc'
|
---|
657 | self.otherIsIterable = True
|
---|
658 |
|
---|
659 | #------------------------------------------------------------------------------
|
---|
660 |
|
---|
661 | class TestOnlySetsGenerator(TestOnlySetsInBinaryOps):
|
---|
662 | def setUp(self):
|
---|
663 | def gen():
|
---|
664 | for i in xrange(0, 10, 2):
|
---|
665 | yield i
|
---|
666 | self.set = Set((1, 2, 3))
|
---|
667 | self.other = gen()
|
---|
668 | self.otherIsIterable = True
|
---|
669 |
|
---|
670 | #------------------------------------------------------------------------------
|
---|
671 |
|
---|
672 | class TestOnlySetsofSets(TestOnlySetsInBinaryOps):
|
---|
673 | def setUp(self):
|
---|
674 | self.set = Set((1, 2, 3))
|
---|
675 | self.other = [Set('ab'), ImmutableSet('cd')]
|
---|
676 | self.otherIsIterable = True
|
---|
677 |
|
---|
678 | #==============================================================================
|
---|
679 |
|
---|
680 | class TestCopying(unittest.TestCase):
|
---|
681 |
|
---|
682 | def test_copy(self):
|
---|
683 | dup = self.set.copy()
|
---|
684 | self.assertEqual(len(dup), len(self.set))
|
---|
685 | dup_list = sorted(dup)
|
---|
686 | set_list = sorted(self.set)
|
---|
687 | self.assertEqual(len(dup_list), len(set_list))
|
---|
688 | for i, el in enumerate(dup_list):
|
---|
689 | self.assertIs(el, set_list[i])
|
---|
690 |
|
---|
691 | def test_deep_copy(self):
|
---|
692 | dup = copy.deepcopy(self.set)
|
---|
693 | self.assertSetEqual(dup, self.set)
|
---|
694 |
|
---|
695 | #------------------------------------------------------------------------------
|
---|
696 |
|
---|
697 | class TestCopyingEmpty(TestCopying):
|
---|
698 | def setUp(self):
|
---|
699 | self.set = Set()
|
---|
700 |
|
---|
701 | #------------------------------------------------------------------------------
|
---|
702 |
|
---|
703 | class TestCopyingSingleton(TestCopying):
|
---|
704 | def setUp(self):
|
---|
705 | self.set = Set(["hello"])
|
---|
706 |
|
---|
707 | #------------------------------------------------------------------------------
|
---|
708 |
|
---|
709 | class TestCopyingTriple(TestCopying):
|
---|
710 | def setUp(self):
|
---|
711 | self.set = Set(["zero", 0, None])
|
---|
712 |
|
---|
713 | def test_copy(self):
|
---|
714 | with test_support.check_py3k_warnings():
|
---|
715 | super(TestCopyingTriple, self).test_copy()
|
---|
716 |
|
---|
717 | #------------------------------------------------------------------------------
|
---|
718 |
|
---|
719 | class TestCopyingTuple(TestCopying):
|
---|
720 | def setUp(self):
|
---|
721 | self.set = Set([(1, 2)])
|
---|
722 |
|
---|
723 | #------------------------------------------------------------------------------
|
---|
724 |
|
---|
725 | class TestCopyingNested(TestCopying):
|
---|
726 | def setUp(self):
|
---|
727 | self.set = Set([((1, 2), (3, 4))])
|
---|
728 |
|
---|
729 | #==============================================================================
|
---|
730 |
|
---|
731 | class TestIdentities(unittest.TestCase):
|
---|
732 | def setUp(self):
|
---|
733 | self.a = Set([random.randrange(100) for i in xrange(50)])
|
---|
734 | self.b = Set([random.randrange(100) for i in xrange(50)])
|
---|
735 |
|
---|
736 | def test_binopsVsSubsets(self):
|
---|
737 | a, b = self.a, self.b
|
---|
738 | self.assertTrue(a - b <= a)
|
---|
739 | self.assertTrue(b - a <= b)
|
---|
740 | self.assertTrue(a & b <= a)
|
---|
741 | self.assertTrue(a & b <= b)
|
---|
742 | self.assertTrue(a | b >= a)
|
---|
743 | self.assertTrue(a | b >= b)
|
---|
744 | self.assertTrue(a ^ b <= a | b)
|
---|
745 |
|
---|
746 | def test_commutativity(self):
|
---|
747 | a, b = self.a, self.b
|
---|
748 | self.assertEqual(a&b, b&a)
|
---|
749 | self.assertEqual(a|b, b|a)
|
---|
750 | self.assertEqual(a^b, b^a)
|
---|
751 | if a != b:
|
---|
752 | self.assertNotEqual(a-b, b-a)
|
---|
753 |
|
---|
754 | def test_reflexsive_relations(self):
|
---|
755 | a, zero = self.a, Set()
|
---|
756 | self.assertEqual(a ^ a, zero)
|
---|
757 | self.assertEqual(a - a, zero)
|
---|
758 | self.assertEqual(a | a, a)
|
---|
759 | self.assertEqual(a & a, a)
|
---|
760 | self.assertTrue(a <= a)
|
---|
761 | self.assertTrue(a >= a)
|
---|
762 | self.assertTrue(a == a)
|
---|
763 |
|
---|
764 | def test_summations(self):
|
---|
765 | # check that sums of parts equal the whole
|
---|
766 | a, b = self.a, self.b
|
---|
767 | self.assertEqual((a-b)|(a&b)|(b-a), a|b)
|
---|
768 | self.assertEqual((a&b)|(a^b), a|b)
|
---|
769 | self.assertEqual(a|(b-a), a|b)
|
---|
770 | self.assertEqual((a-b)|b, a|b)
|
---|
771 | self.assertEqual((a-b)|(a&b), a)
|
---|
772 | self.assertEqual((b-a)|(a&b), b)
|
---|
773 | self.assertEqual((a-b)|(b-a), a^b)
|
---|
774 |
|
---|
775 | def test_exclusion(self):
|
---|
776 | # check that inverse operations do not overlap
|
---|
777 | a, b, zero = self.a, self.b, Set()
|
---|
778 | self.assertEqual((a-b)&b, zero)
|
---|
779 | self.assertEqual((b-a)&a, zero)
|
---|
780 | self.assertEqual((a&b)&(a^b), zero)
|
---|
781 |
|
---|
782 | def test_cardinality_relations(self):
|
---|
783 | a, b = self.a, self.b
|
---|
784 | self.assertEqual(len(a), len(a-b) + len(a&b))
|
---|
785 | self.assertEqual(len(b), len(b-a) + len(a&b))
|
---|
786 | self.assertEqual(len(a^b), len(a-b) + len(b-a))
|
---|
787 | self.assertEqual(len(a|b), len(a-b) + len(a&b) + len(b-a))
|
---|
788 | self.assertEqual(len(a^b) + len(a&b), len(a|b))
|
---|
789 |
|
---|
790 | #==============================================================================
|
---|
791 |
|
---|
792 | libreftest = """
|
---|
793 | Example from the Library Reference: Doc/lib/libsets.tex
|
---|
794 |
|
---|
795 | >>> from sets import Set as Base # override _repr to get sorted output
|
---|
796 | >>> class Set(Base):
|
---|
797 | ... def _repr(self):
|
---|
798 | ... return Base._repr(self, sorted=True)
|
---|
799 | >>> engineers = Set(['John', 'Jane', 'Jack', 'Janice'])
|
---|
800 | >>> programmers = Set(['Jack', 'Sam', 'Susan', 'Janice'])
|
---|
801 | >>> managers = Set(['Jane', 'Jack', 'Susan', 'Zack'])
|
---|
802 | >>> employees = engineers | programmers | managers # union
|
---|
803 | >>> engineering_management = engineers & managers # intersection
|
---|
804 | >>> fulltime_management = managers - engineers - programmers # difference
|
---|
805 | >>> engineers.add('Marvin')
|
---|
806 | >>> print engineers
|
---|
807 | Set(['Jack', 'Jane', 'Janice', 'John', 'Marvin'])
|
---|
808 | >>> employees.issuperset(engineers) # superset test
|
---|
809 | False
|
---|
810 | >>> employees.union_update(engineers) # update from another set
|
---|
811 | >>> employees.issuperset(engineers)
|
---|
812 | True
|
---|
813 | >>> for group in [engineers, programmers, managers, employees]:
|
---|
814 | ... group.discard('Susan') # unconditionally remove element
|
---|
815 | ... print group
|
---|
816 | ...
|
---|
817 | Set(['Jack', 'Jane', 'Janice', 'John', 'Marvin'])
|
---|
818 | Set(['Jack', 'Janice', 'Sam'])
|
---|
819 | Set(['Jack', 'Jane', 'Zack'])
|
---|
820 | Set(['Jack', 'Jane', 'Janice', 'John', 'Marvin', 'Sam', 'Zack'])
|
---|
821 | """
|
---|
822 |
|
---|
823 | #==============================================================================
|
---|
824 |
|
---|
825 | __test__ = {'libreftest' : libreftest}
|
---|
826 |
|
---|
827 | def test_main(verbose=None):
|
---|
828 | import doctest
|
---|
829 | from test import test_sets
|
---|
830 | test_support.run_unittest(
|
---|
831 | TestSetOfSets,
|
---|
832 | TestExceptionPropagation,
|
---|
833 | TestBasicOpsEmpty,
|
---|
834 | TestBasicOpsSingleton,
|
---|
835 | TestBasicOpsTuple,
|
---|
836 | TestBasicOpsTriple,
|
---|
837 | TestBinaryOps,
|
---|
838 | TestUpdateOps,
|
---|
839 | TestMutate,
|
---|
840 | TestSubsetEqualEmpty,
|
---|
841 | TestSubsetEqualNonEmpty,
|
---|
842 | TestSubsetEmptyNonEmpty,
|
---|
843 | TestSubsetPartial,
|
---|
844 | TestSubsetNonOverlap,
|
---|
845 | TestOnlySetsNumeric,
|
---|
846 | TestOnlySetsDict,
|
---|
847 | TestOnlySetsOperator,
|
---|
848 | TestOnlySetsTuple,
|
---|
849 | TestOnlySetsString,
|
---|
850 | TestOnlySetsGenerator,
|
---|
851 | TestOnlySetsofSets,
|
---|
852 | TestCopyingEmpty,
|
---|
853 | TestCopyingSingleton,
|
---|
854 | TestCopyingTriple,
|
---|
855 | TestCopyingTuple,
|
---|
856 | TestCopyingNested,
|
---|
857 | TestIdentities,
|
---|
858 | doctest.DocTestSuite(test_sets),
|
---|
859 | )
|
---|
860 |
|
---|
861 | if __name__ == "__main__":
|
---|
862 | test_main(verbose=True)
|
---|