blob: 020f4e2a8161dcbaa99fc283a87c428d4a536ad0 [file] [log] [blame]
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001"""Unit tests for collections.py."""
2
Benjamin Peterson4ad6bd52010-05-21 20:55:22 +00003import unittest, doctest, operator
Raymond Hettingerf6d3e8e2011-03-23 20:33:30 -07004from test.support import TESTFN, forget, unlink
Raymond Hettinger2d32f632009-03-02 21:24:57 +00005import inspect
Benjamin Petersonee8712c2008-05-20 21:35:26 +00006from test import support
Raymond Hettinger426e0522011-01-03 02:12:02 +00007from collections import namedtuple, Counter, OrderedDict, _count_elements
Raymond Hettinger2d32f632009-03-02 21:24:57 +00008from test import mapping_tests
Georg Brandlc28e1fa2008-06-10 19:20:26 +00009import pickle, copy
Raymond Hettinger2d32f632009-03-02 21:24:57 +000010from random import randrange, shuffle
Raymond Hettinger499b2ee2009-05-27 01:53:46 +000011import keyword
12import re
R. David Murray378c0cf2010-02-24 01:46:21 +000013import sys
Raymond Hettinger57d1a882011-02-23 00:46:28 +000014from collections import UserDict
Raymond Hettinger9fe1ccf2011-02-26 01:02:51 +000015from collections import ChainMap
Raymond Hettinger57d1a882011-02-23 00:46:28 +000016from collections.abc import Hashable, Iterable, Iterator
17from collections.abc import Sized, Container, Callable
18from collections.abc import Set, MutableSet
19from collections.abc import Mapping, MutableMapping, KeysView, ItemsView
20from collections.abc import Sequence, MutableSequence
21from collections.abc import ByteString
Guido van Rossumcd16bf62007-06-13 18:07:49 +000022
Raymond Hettinger499e1932011-02-23 07:56:53 +000023
24################################################################################
Raymond Hettinger9fe1ccf2011-02-26 01:02:51 +000025### ChainMap (helper class for configparser and the string module)
Raymond Hettinger499e1932011-02-23 07:56:53 +000026################################################################################
27
28class TestChainMap(unittest.TestCase):
29
30 def test_basics(self):
31 c = ChainMap()
32 c['a'] = 1
33 c['b'] = 2
34 d = c.new_child()
35 d['b'] = 20
36 d['c'] = 30
37 self.assertEqual(d.maps, [{'b':20, 'c':30}, {'a':1, 'b':2}]) # check internal state
38 self.assertEqual(d.items(), dict(a=1, b=20, c=30).items()) # check items/iter/getitem
39 self.assertEqual(len(d), 3) # check len
40 for key in 'abc': # check contains
41 self.assertIn(key, d)
42 for k, v in dict(a=1, b=20, c=30, z=100).items(): # check get
43 self.assertEqual(d.get(k, 100), v)
44
45 del d['b'] # unmask a value
46 self.assertEqual(d.maps, [{'c':30}, {'a':1, 'b':2}]) # check internal state
47 self.assertEqual(d.items(), dict(a=1, b=2, c=30).items()) # check items/iter/getitem
48 self.assertEqual(len(d), 3) # check len
49 for key in 'abc': # check contains
50 self.assertIn(key, d)
51 for k, v in dict(a=1, b=2, c=30, z=100).items(): # check get
52 self.assertEqual(d.get(k, 100), v)
53 self.assertIn(repr(d), [ # check repr
54 type(d).__name__ + "({'c': 30}, {'a': 1, 'b': 2})",
55 type(d).__name__ + "({'c': 30}, {'b': 2, 'a': 1})"
56 ])
57
58 for e in d.copy(), copy.copy(d): # check shallow copies
59 self.assertEqual(d, e)
60 self.assertEqual(d.maps, e.maps)
61 self.assertIsNot(d, e)
62 self.assertIsNot(d.maps[0], e.maps[0])
63 for m1, m2 in zip(d.maps[1:], e.maps[1:]):
64 self.assertIs(m1, m2)
65
66 for e in [pickle.loads(pickle.dumps(d)),
67 copy.deepcopy(d),
68 eval(repr(d))
69 ]: # check deep copies
70 self.assertEqual(d, e)
71 self.assertEqual(d.maps, e.maps)
72 self.assertIsNot(d, e)
73 for m1, m2 in zip(d.maps, e.maps):
74 self.assertIsNot(m1, m2, e)
75
Raymond Hettingerd0321312011-02-26 06:53:58 +000076 f = d.new_child()
77 f['b'] = 5
78 self.assertEqual(f.maps, [{'b': 5}, {'c':30}, {'a':1, 'b':2}])
79 self.assertEqual(f.parents.maps, [{'c':30}, {'a':1, 'b':2}]) # check parents
80 self.assertEqual(f['b'], 5) # find first in chain
81 self.assertEqual(f.parents['b'], 2) # look beyond maps[0]
Raymond Hettinger499e1932011-02-23 07:56:53 +000082
83 def test_contructor(self):
Raymond Hettingerd0321312011-02-26 06:53:58 +000084 self.assertEqual(ChainMap().maps, [{}]) # no-args --> one new dict
Raymond Hettinger499e1932011-02-23 07:56:53 +000085 self.assertEqual(ChainMap({1:2}).maps, [{1:2}]) # 1 arg --> list
86
Raymond Hettingerd0321312011-02-26 06:53:58 +000087 def test_bool(self):
88 self.assertFalse(ChainMap())
89 self.assertFalse(ChainMap({}, {}))
90 self.assertTrue(ChainMap({1:2}, {}))
91 self.assertTrue(ChainMap({}, {1:2}))
92
Raymond Hettinger499e1932011-02-23 07:56:53 +000093 def test_missing(self):
94 class DefaultChainMap(ChainMap):
95 def __missing__(self, key):
96 return 999
97 d = DefaultChainMap(dict(a=1, b=2), dict(b=20, c=30))
98 for k, v in dict(a=1, b=2, c=30, d=999).items():
99 self.assertEqual(d[k], v) # check __getitem__ w/missing
100 for k, v in dict(a=1, b=2, c=30, d=77).items():
101 self.assertEqual(d.get(k, 77), v) # check get() w/ missing
102 for k, v in dict(a=True, b=True, c=True, d=False).items():
103 self.assertEqual(k in d, v) # check __contains__ w/missing
104 self.assertEqual(d.pop('a', 1001), 1, d)
105 self.assertEqual(d.pop('a', 1002), 1002) # check pop() w/missing
106 self.assertEqual(d.popitem(), ('b', 2)) # check popitem() w/missing
107 with self.assertRaises(KeyError):
108 d.popitem()
109
110 def test_dict_coercion(self):
111 d = ChainMap(dict(a=1, b=2), dict(b=20, c=30))
112 self.assertEqual(dict(d), dict(a=1, b=2, c=30))
113 self.assertEqual(dict(d.items()), dict(a=1, b=2, c=30))
114
115
116################################################################################
117### Named Tuples
118################################################################################
119
Georg Brandlc28e1fa2008-06-10 19:20:26 +0000120TestNT = namedtuple('TestNT', 'x y z') # type used for pickle tests
Guido van Rossumd8faa362007-04-27 19:54:29 +0000121
122class TestNamedTuple(unittest.TestCase):
123
124 def test_factory(self):
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000125 Point = namedtuple('Point', 'x y')
Guido van Rossumd8faa362007-04-27 19:54:29 +0000126 self.assertEqual(Point.__name__, 'Point')
Guido van Rossumd8faa362007-04-27 19:54:29 +0000127 self.assertEqual(Point.__slots__, ())
128 self.assertEqual(Point.__module__, __name__)
129 self.assertEqual(Point.__getitem__, tuple.__getitem__)
Christian Heimesfaf2f632008-01-06 16:59:19 +0000130 self.assertEqual(Point._fields, ('x', 'y'))
Raymond Hettinger2ebea412011-03-23 12:52:23 -0700131 self.assertIn('class Point(tuple)', Point._source)
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000132
133 self.assertRaises(ValueError, namedtuple, 'abc%', 'efg ghi') # type has non-alpha char
134 self.assertRaises(ValueError, namedtuple, 'class', 'efg ghi') # type has keyword
135 self.assertRaises(ValueError, namedtuple, '9abc', 'efg ghi') # type starts with digit
136
137 self.assertRaises(ValueError, namedtuple, 'abc', 'efg g%hi') # field with non-alpha char
138 self.assertRaises(ValueError, namedtuple, 'abc', 'abc class') # field has keyword
139 self.assertRaises(ValueError, namedtuple, 'abc', '8efg 9ghi') # field starts with digit
Christian Heimes0449f632007-12-15 01:27:15 +0000140 self.assertRaises(ValueError, namedtuple, 'abc', '_efg ghi') # field with leading underscore
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000141 self.assertRaises(ValueError, namedtuple, 'abc', 'efg efg ghi') # duplicate field
142
143 namedtuple('Point0', 'x1 y2') # Verify that numbers are allowed in names
Christian Heimes0449f632007-12-15 01:27:15 +0000144 namedtuple('_', 'a b c') # Test leading underscores in a typename
Guido van Rossumd8faa362007-04-27 19:54:29 +0000145
Benjamin Petersone9bbc8b2008-09-28 02:06:32 +0000146 nt = namedtuple('nt', 'the quick brown fox') # check unicode input
Benjamin Peterson577473f2010-01-19 00:09:57 +0000147 self.assertNotIn("u'", repr(nt._fields))
Benjamin Petersone9bbc8b2008-09-28 02:06:32 +0000148 nt = namedtuple('nt', ('the', 'quick')) # check unicode input
Benjamin Peterson577473f2010-01-19 00:09:57 +0000149 self.assertNotIn("u'", repr(nt._fields))
Benjamin Petersone9bbc8b2008-09-28 02:06:32 +0000150
Christian Heimesfaf2f632008-01-06 16:59:19 +0000151 self.assertRaises(TypeError, Point._make, [11]) # catch too few args
152 self.assertRaises(TypeError, Point._make, [11, 22, 33]) # catch too many args
153
R. David Murray378c0cf2010-02-24 01:46:21 +0000154 @unittest.skipIf(sys.flags.optimize >= 2,
155 "Docstrings are omitted with -O2 and above")
156 def test_factory_doc_attr(self):
157 Point = namedtuple('Point', 'x y')
158 self.assertEqual(Point.__doc__, 'Point(x, y)')
159
Benjamin Petersona86f2c02009-02-10 02:41:10 +0000160 def test_name_fixer(self):
161 for spec, renamed in [
Raymond Hettinger56145242009-04-02 22:31:59 +0000162 [('efg', 'g%hi'), ('efg', '_1')], # field with non-alpha char
163 [('abc', 'class'), ('abc', '_1')], # field has keyword
164 [('8efg', '9ghi'), ('_0', '_1')], # field starts with digit
165 [('abc', '_efg'), ('abc', '_1')], # field with leading underscore
166 [('abc', 'efg', 'efg', 'ghi'), ('abc', 'efg', '_2', 'ghi')], # duplicate field
167 [('abc', '', 'x'), ('abc', '_1', 'x')], # fieldname is a space
Benjamin Petersona86f2c02009-02-10 02:41:10 +0000168 ]:
169 self.assertEqual(namedtuple('NT', spec, rename=True)._fields, renamed)
170
Guido van Rossumd8faa362007-04-27 19:54:29 +0000171 def test_instance(self):
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000172 Point = namedtuple('Point', 'x y')
Guido van Rossumd8faa362007-04-27 19:54:29 +0000173 p = Point(11, 22)
174 self.assertEqual(p, Point(x=11, y=22))
175 self.assertEqual(p, Point(11, y=22))
176 self.assertEqual(p, Point(y=22, x=11))
177 self.assertEqual(p, Point(*(11, 22)))
178 self.assertEqual(p, Point(**dict(x=11, y=22)))
179 self.assertRaises(TypeError, Point, 1) # too few args
180 self.assertRaises(TypeError, Point, 1, 2, 3) # too many args
181 self.assertRaises(TypeError, eval, 'Point(XXX=1, y=2)', locals()) # wrong keyword argument
182 self.assertRaises(TypeError, eval, 'Point(x=1)', locals()) # missing keyword argument
183 self.assertEqual(repr(p), 'Point(x=11, y=22)')
Benjamin Peterson577473f2010-01-19 00:09:57 +0000184 self.assertNotIn('__dict__', dir(p)) # verify instance has no dict
185 self.assertNotIn('__weakref__', dir(p))
Christian Heimesfaf2f632008-01-06 16:59:19 +0000186 self.assertEqual(p, Point._make([11, 22])) # test _make classmethod
Christian Heimes0449f632007-12-15 01:27:15 +0000187 self.assertEqual(p._fields, ('x', 'y')) # test _fields attribute
188 self.assertEqual(p._replace(x=1), (1, 22)) # test _replace method
189 self.assertEqual(p._asdict(), dict(x=11, y=22)) # test _asdict method
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000190
Guido van Rossum3d392eb2007-11-16 00:35:22 +0000191 try:
Christian Heimesfaf2f632008-01-06 16:59:19 +0000192 p._replace(x=1, error=2)
193 except ValueError:
Guido van Rossum3d392eb2007-11-16 00:35:22 +0000194 pass
195 else:
Christian Heimesfaf2f632008-01-06 16:59:19 +0000196 self._fail('Did not detect an incorrect fieldname')
Guido van Rossum3d392eb2007-11-16 00:35:22 +0000197
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000198 # verify that field string can have commas
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000199 Point = namedtuple('Point', 'x, y')
200 p = Point(x=11, y=22)
201 self.assertEqual(repr(p), 'Point(x=11, y=22)')
202
203 # verify that fieldspec can be a non-string sequence
204 Point = namedtuple('Point', ('x', 'y'))
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000205 p = Point(x=11, y=22)
206 self.assertEqual(repr(p), 'Point(x=11, y=22)')
Guido van Rossumd8faa362007-04-27 19:54:29 +0000207
208 def test_tupleness(self):
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000209 Point = namedtuple('Point', 'x y')
Guido van Rossumd8faa362007-04-27 19:54:29 +0000210 p = Point(11, 22)
211
Ezio Melottie9615932010-01-24 19:26:24 +0000212 self.assertIsInstance(p, tuple)
Guido van Rossumd8faa362007-04-27 19:54:29 +0000213 self.assertEqual(p, (11, 22)) # matches a real tuple
214 self.assertEqual(tuple(p), (11, 22)) # coercable to a real tuple
215 self.assertEqual(list(p), [11, 22]) # coercable to a list
216 self.assertEqual(max(p), 22) # iterable
217 self.assertEqual(max(*p), 22) # star-able
218 x, y = p
219 self.assertEqual(p, (x, y)) # unpacks like a tuple
220 self.assertEqual((p[0], p[1]), (11, 22)) # indexable like a tuple
221 self.assertRaises(IndexError, p.__getitem__, 3)
222
223 self.assertEqual(p.x, x)
224 self.assertEqual(p.y, y)
225 self.assertRaises(AttributeError, eval, 'p.z', locals())
226
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000227 def test_odd_sizes(self):
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000228 Zero = namedtuple('Zero', '')
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000229 self.assertEqual(Zero(), ())
Christian Heimesfaf2f632008-01-06 16:59:19 +0000230 self.assertEqual(Zero._make([]), ())
Christian Heimes99170a52007-12-19 02:07:34 +0000231 self.assertEqual(repr(Zero()), 'Zero()')
232 self.assertEqual(Zero()._asdict(), {})
233 self.assertEqual(Zero()._fields, ())
234
Guido van Rossum8ce8a782007-11-01 19:42:39 +0000235 Dot = namedtuple('Dot', 'd')
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000236 self.assertEqual(Dot(1), (1,))
Christian Heimesfaf2f632008-01-06 16:59:19 +0000237 self.assertEqual(Dot._make([1]), (1,))
Christian Heimes99170a52007-12-19 02:07:34 +0000238 self.assertEqual(Dot(1).d, 1)
239 self.assertEqual(repr(Dot(1)), 'Dot(d=1)')
240 self.assertEqual(Dot(1)._asdict(), {'d':1})
241 self.assertEqual(Dot(1)._replace(d=999), (999,))
242 self.assertEqual(Dot(1)._fields, ('d',))
Thomas Wouters1b7f8912007-09-19 03:06:30 +0000243
Georg Brandlc28e1fa2008-06-10 19:20:26 +0000244 # n = 5000
Christian Heimes99170a52007-12-19 02:07:34 +0000245 n = 254 # SyntaxError: more than 255 arguments:
246 import string, random
Georg Brandlb533e262008-05-25 18:19:30 +0000247 names = list(set(''.join([random.choice(string.ascii_letters)
248 for j in range(10)]) for i in range(n)))
249 n = len(names)
Christian Heimes99170a52007-12-19 02:07:34 +0000250 Big = namedtuple('Big', names)
251 b = Big(*range(n))
252 self.assertEqual(b, tuple(range(n)))
Christian Heimesfaf2f632008-01-06 16:59:19 +0000253 self.assertEqual(Big._make(range(n)), tuple(range(n)))
Christian Heimes99170a52007-12-19 02:07:34 +0000254 for pos, name in enumerate(names):
255 self.assertEqual(getattr(b, name), pos)
256 repr(b) # make sure repr() doesn't blow-up
257 d = b._asdict()
258 d_expected = dict(zip(names, range(n)))
259 self.assertEqual(d, d_expected)
260 b2 = b._replace(**dict([(names[1], 999),(names[-5], 42)]))
261 b2_expected = list(range(n))
262 b2_expected[1] = 999
263 b2_expected[-5] = 42
264 self.assertEqual(b2, tuple(b2_expected))
265 self.assertEqual(b._fields, tuple(names))
Guido van Rossumd8faa362007-04-27 19:54:29 +0000266
Georg Brandlc28e1fa2008-06-10 19:20:26 +0000267 def test_pickle(self):
268 p = TestNT(x=10, y=20, z=30)
269 for module in (pickle,):
270 loads = getattr(module, 'loads')
271 dumps = getattr(module, 'dumps')
272 for protocol in -1, 0, 1, 2:
273 q = loads(dumps(p, protocol))
274 self.assertEqual(p, q)
275 self.assertEqual(p._fields, q._fields)
276
277 def test_copy(self):
278 p = TestNT(x=10, y=20, z=30)
279 for copier in copy.copy, copy.deepcopy:
280 q = copier(p)
281 self.assertEqual(p, q)
282 self.assertEqual(p._fields, q._fields)
283
Raymond Hettinger089ba7f2009-05-27 00:38:24 +0000284 def test_name_conflicts(self):
285 # Some names like "self", "cls", "tuple", "itemgetter", and "property"
286 # failed when used as field names. Test to make sure these now work.
287 T = namedtuple('T', 'itemgetter property self cls tuple')
288 t = T(1, 2, 3, 4, 5)
289 self.assertEqual(t, (1,2,3,4,5))
290 newt = t._replace(itemgetter=10, property=20, self=30, cls=40, tuple=50)
291 self.assertEqual(newt, (10,20,30,40,50))
292
Raymond Hettinger499b2ee2009-05-27 01:53:46 +0000293 # Broader test of all interesting names in a template
294 with support.captured_stdout() as template:
295 T = namedtuple('T', 'x', verbose=True)
296 words = set(re.findall('[A-Za-z]+', template.getvalue()))
297 words -= set(keyword.kwlist)
298 T = namedtuple('T', words)
299 # test __new__
300 values = tuple(range(len(words)))
301 t = T(*values)
302 self.assertEqual(t, values)
303 t = T(**dict(zip(T._fields, values)))
304 self.assertEqual(t, values)
305 # test _make
306 t = T._make(values)
307 self.assertEqual(t, values)
308 # exercise __repr__
309 repr(t)
310 # test _asdict
311 self.assertEqual(t._asdict(), dict(zip(T._fields, values)))
312 # test _replace
313 t = T._make(values)
314 newvalues = tuple(v*10 for v in values)
315 newt = t._replace(**dict(zip(T._fields, newvalues)))
316 self.assertEqual(newt, newvalues)
317 # test _fields
318 self.assertEqual(T._fields, tuple(words))
319 # test __getnewargs__
320 self.assertEqual(t.__getnewargs__(), values)
321
Raymond Hettingerd331ce92010-08-08 01:13:42 +0000322 def test_repr(self):
323 with support.captured_stdout() as template:
324 A = namedtuple('A', 'x', verbose=True)
325 self.assertEqual(repr(A(1)), 'A(x=1)')
326 # repr should show the name of the subclass
327 class B(A):
328 pass
329 self.assertEqual(repr(B(1)), 'B(x=1)')
330
Raymond Hettingerf6d3e8e2011-03-23 20:33:30 -0700331 def test_source(self):
332 # verify that _source can be run through exec()
Raymond Hettingerd4652fa2011-03-24 09:45:43 -0700333 tmp = namedtuple('NTColor', 'red green blue')
334 globals().pop('NTColor', None) # remove artifacts from other tests
335 self.assertNotIn('NTColor', globals())
Raymond Hettingerf6d3e8e2011-03-23 20:33:30 -0700336 exec(tmp._source, globals())
Raymond Hettingerd4652fa2011-03-24 09:45:43 -0700337 self.assertIn('NTColor', globals())
338 c = NTColor(10, 20, 30)
Raymond Hettingerf6d3e8e2011-03-23 20:33:30 -0700339 self.assertEqual((c.red, c.green, c.blue), (10, 20, 30))
Raymond Hettingerd4652fa2011-03-24 09:45:43 -0700340 self.assertEqual(NTColor._fields, ('red', 'green', 'blue'))
341 globals().pop('NTColor', None) # clean-up after this test
342 self.assertNotIn('NTColor', globals())
Raymond Hettingerf6d3e8e2011-03-23 20:33:30 -0700343
344 def test_source_importable(self):
345 tmp = namedtuple('Color', 'hue sat val')
346
347 compiled = None
348 source = TESTFN + '.py'
349 with open(source, 'w') as f:
350 print(tmp._source, file=f)
351
352 if TESTFN in sys.modules:
353 del sys.modules[TESTFN]
354 try:
355 mod = __import__(TESTFN)
356 compiled = mod.__file__
357 Color = mod.Color
358 c = Color(10, 20, 30)
359 self.assertEqual((c.hue, c.sat, c.val), (10, 20, 30))
360 self.assertEqual(Color._fields, ('hue', 'sat', 'val'))
361 finally:
362 forget(TESTFN)
363 if compiled:
364 unlink(compiled)
365 unlink(source)
366
Raymond Hettingerd331ce92010-08-08 01:13:42 +0000367
Raymond Hettinger499e1932011-02-23 07:56:53 +0000368################################################################################
369### Abstract Base Classes
370################################################################################
371
Raymond Hettingerae650182009-01-28 23:33:59 +0000372class ABCTestCase(unittest.TestCase):
373
374 def validate_abstract_methods(self, abc, *names):
375 methodstubs = dict.fromkeys(names, lambda s, *args: 0)
376
377 # everything should work will all required methods are present
378 C = type('C', (abc,), methodstubs)
379 C()
380
381 # instantiation should fail if a required method is missing
382 for name in names:
383 stubs = methodstubs.copy()
384 del stubs[name]
385 C = type('C', (abc,), stubs)
386 self.assertRaises(TypeError, C, name)
387
Florent Xiclunace153f62010-03-08 15:34:35 +0000388 def validate_isinstance(self, abc, name):
389 stub = lambda s, *args: 0
390
391 C = type('C', (object,), {'__hash__': None})
392 setattr(C, name, stub)
393 self.assertIsInstance(C(), abc)
394 self.assertTrue(issubclass(C, abc))
395
396 C = type('C', (object,), {'__hash__': None})
397 self.assertNotIsInstance(C(), abc)
398 self.assertFalse(issubclass(C, abc))
Raymond Hettingerae650182009-01-28 23:33:59 +0000399
Benjamin Peterson4ad6bd52010-05-21 20:55:22 +0000400 def validate_comparison(self, instance):
401 ops = ['lt', 'gt', 'le', 'ge', 'ne', 'or', 'and', 'xor', 'sub']
402 operators = {}
403 for op in ops:
404 name = '__' + op + '__'
405 operators[name] = getattr(operator, name)
406
407 class Other:
408 def __init__(self):
409 self.right_side = False
410 def __eq__(self, other):
411 self.right_side = True
412 return True
413 __lt__ = __eq__
414 __gt__ = __eq__
415 __le__ = __eq__
416 __ge__ = __eq__
417 __ne__ = __eq__
418 __ror__ = __eq__
419 __rand__ = __eq__
420 __rxor__ = __eq__
421 __rsub__ = __eq__
422
423 for name, op in operators.items():
424 if not hasattr(instance, name):
425 continue
426 other = Other()
427 op(instance, other)
428 self.assertTrue(other.right_side,'Right side not called for %s.%s'
429 % (type(instance), name))
430
Raymond Hettingerae650182009-01-28 23:33:59 +0000431class TestOneTrickPonyABCs(ABCTestCase):
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000432
433 def test_Hashable(self):
434 # Check some non-hashables
Guido van Rossum254348e2007-11-21 19:29:53 +0000435 non_samples = [bytearray(), list(), set(), dict()]
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000436 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000437 self.assertNotIsInstance(x, Hashable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000438 self.assertFalse(issubclass(type(x), Hashable), repr(type(x)))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000439 # Check some hashables
440 samples = [None,
441 int(), float(), complex(),
Guido van Rossum07d4e782007-07-03 16:59:47 +0000442 str(),
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000443 tuple(), frozenset(),
Guido van Rossum98297ee2007-11-06 21:34:58 +0000444 int, list, object, type, bytes()
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000445 ]
446 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000447 self.assertIsInstance(x, Hashable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000448 self.assertTrue(issubclass(type(x), Hashable), repr(type(x)))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000449 self.assertRaises(TypeError, Hashable)
450 # Check direct subclassing
451 class H(Hashable):
452 def __hash__(self):
453 return super().__hash__()
454 self.assertEqual(hash(H()), 0)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000455 self.assertFalse(issubclass(int, H))
Raymond Hettingerae650182009-01-28 23:33:59 +0000456 self.validate_abstract_methods(Hashable, '__hash__')
Florent Xiclunace153f62010-03-08 15:34:35 +0000457 self.validate_isinstance(Hashable, '__hash__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000458
459 def test_Iterable(self):
460 # Check some non-iterables
461 non_samples = [None, 42, 3.14, 1j]
462 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000463 self.assertNotIsInstance(x, Iterable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000464 self.assertFalse(issubclass(type(x), Iterable), repr(type(x)))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000465 # Check some iterables
Guido van Rossum07d4e782007-07-03 16:59:47 +0000466 samples = [bytes(), str(),
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000467 tuple(), list(), set(), frozenset(), dict(),
468 dict().keys(), dict().items(), dict().values(),
469 (lambda: (yield))(),
470 (x for x in []),
471 ]
472 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000473 self.assertIsInstance(x, Iterable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000474 self.assertTrue(issubclass(type(x), Iterable), repr(type(x)))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000475 # Check direct subclassing
476 class I(Iterable):
477 def __iter__(self):
478 return super().__iter__()
479 self.assertEqual(list(I()), [])
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000480 self.assertFalse(issubclass(str, I))
Raymond Hettingerae650182009-01-28 23:33:59 +0000481 self.validate_abstract_methods(Iterable, '__iter__')
Florent Xiclunace153f62010-03-08 15:34:35 +0000482 self.validate_isinstance(Iterable, '__iter__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000483
484 def test_Iterator(self):
Guido van Rossum07d4e782007-07-03 16:59:47 +0000485 non_samples = [None, 42, 3.14, 1j, b"", "", (), [], {}, set()]
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000486 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000487 self.assertNotIsInstance(x, Iterator)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000488 self.assertFalse(issubclass(type(x), Iterator), repr(type(x)))
Guido van Rossum07d4e782007-07-03 16:59:47 +0000489 samples = [iter(bytes()), iter(str()),
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000490 iter(tuple()), iter(list()), iter(dict()),
491 iter(set()), iter(frozenset()),
492 iter(dict().keys()), iter(dict().items()),
493 iter(dict().values()),
494 (lambda: (yield))(),
495 (x for x in []),
496 ]
497 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000498 self.assertIsInstance(x, Iterator)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000499 self.assertTrue(issubclass(type(x), Iterator), repr(type(x)))
Raymond Hettingeread22222010-11-29 03:56:12 +0000500 self.validate_abstract_methods(Iterator, '__next__', '__iter__')
501
502 # Issue 10565
503 class NextOnly:
504 def __next__(self):
505 yield 1
506 raise StopIteration
507 self.assertNotIsInstance(NextOnly(), Iterator)
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000508
509 def test_Sized(self):
510 non_samples = [None, 42, 3.14, 1j,
511 (lambda: (yield))(),
512 (x for x in []),
513 ]
514 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000515 self.assertNotIsInstance(x, Sized)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000516 self.assertFalse(issubclass(type(x), Sized), repr(type(x)))
Guido van Rossum07d4e782007-07-03 16:59:47 +0000517 samples = [bytes(), str(),
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000518 tuple(), list(), set(), frozenset(), dict(),
519 dict().keys(), dict().items(), dict().values(),
520 ]
521 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000522 self.assertIsInstance(x, Sized)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000523 self.assertTrue(issubclass(type(x), Sized), repr(type(x)))
Raymond Hettingerae650182009-01-28 23:33:59 +0000524 self.validate_abstract_methods(Sized, '__len__')
Florent Xiclunace153f62010-03-08 15:34:35 +0000525 self.validate_isinstance(Sized, '__len__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000526
527 def test_Container(self):
528 non_samples = [None, 42, 3.14, 1j,
529 (lambda: (yield))(),
530 (x for x in []),
531 ]
532 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000533 self.assertNotIsInstance(x, Container)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000534 self.assertFalse(issubclass(type(x), Container), repr(type(x)))
Guido van Rossum07d4e782007-07-03 16:59:47 +0000535 samples = [bytes(), str(),
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000536 tuple(), list(), set(), frozenset(), dict(),
537 dict().keys(), dict().items(),
538 ]
539 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000540 self.assertIsInstance(x, Container)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000541 self.assertTrue(issubclass(type(x), Container), repr(type(x)))
Raymond Hettingerae650182009-01-28 23:33:59 +0000542 self.validate_abstract_methods(Container, '__contains__')
Florent Xiclunace153f62010-03-08 15:34:35 +0000543 self.validate_isinstance(Container, '__contains__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000544
545 def test_Callable(self):
546 non_samples = [None, 42, 3.14, 1j,
547 "", b"", (), [], {}, set(),
548 (lambda: (yield))(),
549 (x for x in []),
550 ]
551 for x in non_samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000552 self.assertNotIsInstance(x, Callable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000553 self.assertFalse(issubclass(type(x), Callable), repr(type(x)))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000554 samples = [lambda: None,
555 type, int, object,
556 len,
557 list.append, [].append,
558 ]
559 for x in samples:
Ezio Melottie9615932010-01-24 19:26:24 +0000560 self.assertIsInstance(x, Callable)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000561 self.assertTrue(issubclass(type(x), Callable), repr(type(x)))
Raymond Hettingerae650182009-01-28 23:33:59 +0000562 self.validate_abstract_methods(Callable, '__call__')
Florent Xiclunace153f62010-03-08 15:34:35 +0000563 self.validate_isinstance(Callable, '__call__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000564
565 def test_direct_subclassing(self):
566 for B in Hashable, Iterable, Iterator, Sized, Container, Callable:
567 class C(B):
568 pass
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000569 self.assertTrue(issubclass(C, B))
570 self.assertFalse(issubclass(int, C))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000571
572 def test_registration(self):
573 for B in Hashable, Iterable, Iterator, Sized, Container, Callable:
574 class C:
575 __hash__ = None # Make sure it isn't hashable by default
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000576 self.assertFalse(issubclass(C, B), B.__name__)
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000577 B.register(C)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000578 self.assertTrue(issubclass(C, B))
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000579
Raymond Hettinger3f10a952009-04-01 19:05:50 +0000580class WithSet(MutableSet):
581
582 def __init__(self, it=()):
583 self.data = set(it)
584
585 def __len__(self):
586 return len(self.data)
587
588 def __iter__(self):
589 return iter(self.data)
590
591 def __contains__(self, item):
592 return item in self.data
593
594 def add(self, item):
595 self.data.add(item)
596
597 def discard(self, item):
598 self.data.discard(item)
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000599
Raymond Hettingerae650182009-01-28 23:33:59 +0000600class TestCollectionABCs(ABCTestCase):
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000601
602 # XXX For now, we only test some virtual inheritance properties.
603 # We should also test the proper behavior of the collection ABCs
604 # as real base classes or mix-in classes.
605
606 def test_Set(self):
607 for sample in [set, frozenset]:
Ezio Melottie9615932010-01-24 19:26:24 +0000608 self.assertIsInstance(sample(), Set)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000609 self.assertTrue(issubclass(sample, Set))
Raymond Hettingerae650182009-01-28 23:33:59 +0000610 self.validate_abstract_methods(Set, '__contains__', '__iter__', '__len__')
Benjamin Peterson4ad6bd52010-05-21 20:55:22 +0000611 class MySet(Set):
612 def __contains__(self, x):
613 return False
614 def __len__(self):
615 return 0
616 def __iter__(self):
617 return iter([])
618 self.validate_comparison(MySet())
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000619
Benjamin Peterson41181742008-07-02 20:22:54 +0000620 def test_hash_Set(self):
621 class OneTwoThreeSet(Set):
622 def __init__(self):
623 self.contents = [1, 2, 3]
624 def __contains__(self, x):
625 return x in self.contents
626 def __len__(self):
627 return len(self.contents)
628 def __iter__(self):
629 return iter(self.contents)
630 def __hash__(self):
631 return self._hash()
632 a, b = OneTwoThreeSet(), OneTwoThreeSet()
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000633 self.assertTrue(hash(a) == hash(b))
Benjamin Peterson41181742008-07-02 20:22:54 +0000634
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000635 def test_MutableSet(self):
Ezio Melottie9615932010-01-24 19:26:24 +0000636 self.assertIsInstance(set(), MutableSet)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000637 self.assertTrue(issubclass(set, MutableSet))
Ezio Melottie9615932010-01-24 19:26:24 +0000638 self.assertNotIsInstance(frozenset(), MutableSet)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000639 self.assertFalse(issubclass(frozenset, MutableSet))
Raymond Hettingerae650182009-01-28 23:33:59 +0000640 self.validate_abstract_methods(MutableSet, '__contains__', '__iter__', '__len__',
641 'add', 'discard')
642
Raymond Hettinger3f10a952009-04-01 19:05:50 +0000643 def test_issue_5647(self):
644 # MutableSet.__iand__ mutated the set during iteration
645 s = WithSet('abcd')
646 s &= WithSet('cdef') # This used to fail
647 self.assertEqual(set(s), set('cd'))
648
Raymond Hettingerae650182009-01-28 23:33:59 +0000649 def test_issue_4920(self):
650 # MutableSet.pop() method did not work
Raymond Hettinger57d1a882011-02-23 00:46:28 +0000651 class MySet(MutableSet):
Raymond Hettingerae650182009-01-28 23:33:59 +0000652 __slots__=['__s']
653 def __init__(self,items=None):
654 if items is None:
655 items=[]
656 self.__s=set(items)
657 def __contains__(self,v):
658 return v in self.__s
659 def __iter__(self):
660 return iter(self.__s)
661 def __len__(self):
662 return len(self.__s)
663 def add(self,v):
664 result=v not in self.__s
665 self.__s.add(v)
666 return result
667 def discard(self,v):
668 result=v in self.__s
669 self.__s.discard(v)
670 return result
671 def __repr__(self):
672 return "MySet(%s)" % repr(list(self))
673 s = MySet([5,43,2,1])
674 self.assertEqual(s.pop(), 1)
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000675
Daniel Stutzbach31da5b22010-08-24 20:49:57 +0000676 def test_issue8750(self):
677 empty = WithSet()
678 full = WithSet(range(10))
679 s = WithSet(full)
680 s -= s
681 self.assertEqual(s, empty)
682 s = WithSet(full)
683 s ^= s
684 self.assertEqual(s, empty)
685 s = WithSet(full)
686 s &= s
687 self.assertEqual(s, full)
688 s |= s
689 self.assertEqual(s, full)
690
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000691 def test_Mapping(self):
692 for sample in [dict]:
Ezio Melottie9615932010-01-24 19:26:24 +0000693 self.assertIsInstance(sample(), Mapping)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000694 self.assertTrue(issubclass(sample, Mapping))
Raymond Hettingerae650182009-01-28 23:33:59 +0000695 self.validate_abstract_methods(Mapping, '__contains__', '__iter__', '__len__',
696 '__getitem__')
Raymond Hettinger57d1a882011-02-23 00:46:28 +0000697 class MyMapping(Mapping):
Benjamin Peterson4ad6bd52010-05-21 20:55:22 +0000698 def __len__(self):
699 return 0
700 def __getitem__(self, i):
701 raise IndexError
702 def __iter__(self):
703 return iter(())
704 self.validate_comparison(MyMapping())
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000705
706 def test_MutableMapping(self):
707 for sample in [dict]:
Ezio Melottie9615932010-01-24 19:26:24 +0000708 self.assertIsInstance(sample(), MutableMapping)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000709 self.assertTrue(issubclass(sample, MutableMapping))
Raymond Hettingerae650182009-01-28 23:33:59 +0000710 self.validate_abstract_methods(MutableMapping, '__contains__', '__iter__', '__len__',
711 '__getitem__', '__setitem__', '__delitem__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000712
Raymond Hettinger9117c752010-08-22 07:44:24 +0000713 def test_MutableMapping_subclass(self):
714 # Test issue 9214
715 mymap = UserDict()
716 mymap['red'] = 5
717 self.assertIsInstance(mymap.keys(), Set)
718 self.assertIsInstance(mymap.keys(), KeysView)
719 self.assertIsInstance(mymap.items(), Set)
720 self.assertIsInstance(mymap.items(), ItemsView)
721
722 mymap = UserDict()
723 mymap['red'] = 5
724 z = mymap.keys() | {'orange'}
725 self.assertIsInstance(z, set)
726 list(z)
727 mymap['blue'] = 7 # Shouldn't affect 'z'
728 self.assertEqual(sorted(z), ['orange', 'red'])
729
730 mymap = UserDict()
731 mymap['red'] = 5
732 z = mymap.items() | {('orange', 3)}
733 self.assertIsInstance(z, set)
734 list(z)
735 mymap['blue'] = 7 # Shouldn't affect 'z'
736 self.assertEqual(sorted(z), [('orange', 3), ('red', 5)])
737
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000738 def test_Sequence(self):
739 for sample in [tuple, list, bytes, str]:
Ezio Melottie9615932010-01-24 19:26:24 +0000740 self.assertIsInstance(sample(), Sequence)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000741 self.assertTrue(issubclass(sample, Sequence))
Ezio Melottie9615932010-01-24 19:26:24 +0000742 self.assertIsInstance(range(10), Sequence)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000743 self.assertTrue(issubclass(range, Sequence))
744 self.assertTrue(issubclass(str, Sequence))
Raymond Hettingerae650182009-01-28 23:33:59 +0000745 self.validate_abstract_methods(Sequence, '__contains__', '__iter__', '__len__',
746 '__getitem__')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000747
Guido van Rossumd05eb002007-11-21 22:26:24 +0000748 def test_ByteString(self):
749 for sample in [bytes, bytearray]:
Ezio Melottie9615932010-01-24 19:26:24 +0000750 self.assertIsInstance(sample(), ByteString)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000751 self.assertTrue(issubclass(sample, ByteString))
Guido van Rossumd05eb002007-11-21 22:26:24 +0000752 for sample in [str, list, tuple]:
Ezio Melottie9615932010-01-24 19:26:24 +0000753 self.assertNotIsInstance(sample(), ByteString)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000754 self.assertFalse(issubclass(sample, ByteString))
Ezio Melottie9615932010-01-24 19:26:24 +0000755 self.assertNotIsInstance(memoryview(b""), ByteString)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000756 self.assertFalse(issubclass(memoryview, ByteString))
Guido van Rossumd05eb002007-11-21 22:26:24 +0000757
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000758 def test_MutableSequence(self):
Guido van Rossumd05eb002007-11-21 22:26:24 +0000759 for sample in [tuple, str, bytes]:
Ezio Melottie9615932010-01-24 19:26:24 +0000760 self.assertNotIsInstance(sample(), MutableSequence)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000761 self.assertFalse(issubclass(sample, MutableSequence))
Guido van Rossumd05eb002007-11-21 22:26:24 +0000762 for sample in [list, bytearray]:
Ezio Melottie9615932010-01-24 19:26:24 +0000763 self.assertIsInstance(sample(), MutableSequence)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000764 self.assertTrue(issubclass(sample, MutableSequence))
765 self.assertFalse(issubclass(str, MutableSequence))
Raymond Hettingerae650182009-01-28 23:33:59 +0000766 self.validate_abstract_methods(MutableSequence, '__contains__', '__iter__',
767 '__len__', '__getitem__', '__setitem__', '__delitem__', 'insert')
Guido van Rossumcd16bf62007-06-13 18:07:49 +0000768
Eli Bendersky0716a572011-03-04 10:38:14 +0000769 def test_MutableSequence_mixins(self):
770 # Test the mixins of MutableSequence by creating a miminal concrete
771 # class inherited from it.
772 class MutableSequenceSubclass(MutableSequence):
773 def __init__(self):
774 self.lst = []
775
776 def __setitem__(self, index, value):
777 self.lst[index] = value
778
779 def __getitem__(self, index):
780 return self.lst[index]
781
782 def __len__(self):
783 return len(self.lst)
784
785 def __delitem__(self, index):
786 del self.lst[index]
787
788 def insert(self, index, value):
789 self.lst.insert(index, value)
790
791 mss = MutableSequenceSubclass()
792 mss.append(0)
793 mss.extend((1, 2, 3, 4))
794 self.assertEqual(len(mss), 5)
795 self.assertEqual(mss[3], 3)
796 mss.reverse()
797 self.assertEqual(mss[3], 1)
798 mss.pop()
799 self.assertEqual(len(mss), 4)
800 mss.remove(3)
801 self.assertEqual(len(mss), 3)
802 mss += (10, 20, 30)
803 self.assertEqual(len(mss), 6)
804 self.assertEqual(mss[-1], 30)
805 mss.clear()
806 self.assertEqual(len(mss), 0)
Raymond Hettinger499e1932011-02-23 07:56:53 +0000807
808################################################################################
809### Counter
810################################################################################
811
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000812class TestCounter(unittest.TestCase):
813
814 def test_basics(self):
815 c = Counter('abcaba')
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000816 self.assertEqual(c, Counter({'a':3 , 'b': 2, 'c': 1}))
817 self.assertEqual(c, Counter(a=3, b=2, c=1))
Ezio Melottie9615932010-01-24 19:26:24 +0000818 self.assertIsInstance(c, dict)
819 self.assertIsInstance(c, Mapping)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000820 self.assertTrue(issubclass(Counter, dict))
821 self.assertTrue(issubclass(Counter, Mapping))
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000822 self.assertEqual(len(c), 3)
823 self.assertEqual(sum(c.values()), 6)
824 self.assertEqual(sorted(c.values()), [1, 2, 3])
825 self.assertEqual(sorted(c.keys()), ['a', 'b', 'c'])
826 self.assertEqual(sorted(c), ['a', 'b', 'c'])
827 self.assertEqual(sorted(c.items()),
828 [('a', 3), ('b', 2), ('c', 1)])
829 self.assertEqual(c['b'], 2)
830 self.assertEqual(c['z'], 0)
831 self.assertEqual(c.__contains__('c'), True)
832 self.assertEqual(c.__contains__('z'), False)
833 self.assertEqual(c.get('b', 10), 2)
834 self.assertEqual(c.get('z', 10), 10)
835 self.assertEqual(c, dict(a=3, b=2, c=1))
836 self.assertEqual(repr(c), "Counter({'a': 3, 'b': 2, 'c': 1})")
837 self.assertEqual(c.most_common(), [('a', 3), ('b', 2), ('c', 1)])
838 for i in range(5):
839 self.assertEqual(c.most_common(i),
840 [('a', 3), ('b', 2), ('c', 1)][:i])
841 self.assertEqual(''.join(sorted(c.elements())), 'aaabbc')
842 c['a'] += 1 # increment an existing value
843 c['b'] -= 2 # sub existing value to zero
844 del c['c'] # remove an entry
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000845 del c['c'] # make sure that del doesn't raise KeyError
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000846 c['d'] -= 2 # sub from a missing value
847 c['e'] = -5 # directly assign a missing value
848 c['f'] += 4 # add to a missing value
849 self.assertEqual(c, dict(a=4, b=0, d=-2, e=-5, f=4))
850 self.assertEqual(''.join(sorted(c.elements())), 'aaaaffff')
851 self.assertEqual(c.pop('f'), 4)
Ezio Melottib58e0bd2010-01-23 15:40:09 +0000852 self.assertNotIn('f', c)
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000853 for i in range(3):
854 elem, cnt = c.popitem()
Ezio Melottib58e0bd2010-01-23 15:40:09 +0000855 self.assertNotIn(elem, c)
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000856 c.clear()
857 self.assertEqual(c, {})
858 self.assertEqual(repr(c), 'Counter()')
859 self.assertRaises(NotImplementedError, Counter.fromkeys, 'abc')
860 self.assertRaises(TypeError, hash, c)
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000861 c.update(dict(a=5, b=3))
862 c.update(c=1)
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000863 c.update(Counter('a' * 50 + 'b' * 30))
864 c.update() # test case with no args
865 c.__init__('a' * 500 + 'b' * 300)
866 c.__init__('cdc')
867 c.__init__()
868 self.assertEqual(c, dict(a=555, b=333, c=3, d=1))
869 self.assertEqual(c.setdefault('d', 5), 1)
870 self.assertEqual(c['d'], 1)
871 self.assertEqual(c.setdefault('e', 5), 5)
872 self.assertEqual(c['e'], 5)
873
874 def test_copying(self):
875 # Check that counters are copyable, deepcopyable, picklable, and
876 #have a repr/eval round-trip
877 words = Counter('which witch had which witches wrist watch'.split())
878 update_test = Counter()
879 update_test.update(words)
880 for i, dup in enumerate([
881 words.copy(),
882 copy.copy(words),
883 copy.deepcopy(words),
884 pickle.loads(pickle.dumps(words, 0)),
885 pickle.loads(pickle.dumps(words, 1)),
886 pickle.loads(pickle.dumps(words, 2)),
887 pickle.loads(pickle.dumps(words, -1)),
888 eval(repr(words)),
889 update_test,
890 Counter(words),
891 ]):
892 msg = (i, dup, words)
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000893 self.assertTrue(dup is not words)
Ezio Melottib3aedd42010-11-20 19:04:17 +0000894 self.assertEqual(dup, words)
895 self.assertEqual(len(dup), len(words))
896 self.assertEqual(type(dup), type(words))
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000897
898 def test_conversions(self):
899 # Convert to: set, list, dict
900 s = 'she sells sea shells by the sea shore'
901 self.assertEqual(sorted(Counter(s).elements()), sorted(s))
902 self.assertEqual(sorted(Counter(s)), sorted(set(s)))
903 self.assertEqual(dict(Counter(s)), dict(Counter(s).items()))
904 self.assertEqual(set(Counter(s)), set(s))
905
Raymond Hettinger670eaec2009-01-21 23:14:07 +0000906 def test_invariant_for_the_in_operator(self):
907 c = Counter(a=10, b=-2, c=0)
908 for elem in c:
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000909 self.assertTrue(elem in c)
Benjamin Peterson577473f2010-01-19 00:09:57 +0000910 self.assertIn(elem, c)
Raymond Hettinger670eaec2009-01-21 23:14:07 +0000911
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000912 def test_multiset_operations(self):
913 # Verify that adding a zero counter will strip zeros and negatives
914 c = Counter(a=10, b=-2, c=0) + Counter()
915 self.assertEqual(dict(c), dict(a=10))
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000916
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000917 elements = 'abcd'
918 for i in range(1000):
919 # test random pairs of multisets
920 p = Counter(dict((elem, randrange(-2,4)) for elem in elements))
Raymond Hettingere0d1b9f2009-01-21 20:36:27 +0000921 p.update(e=1, f=-1, g=0)
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000922 q = Counter(dict((elem, randrange(-2,4)) for elem in elements))
Raymond Hettingere0d1b9f2009-01-21 20:36:27 +0000923 q.update(h=1, i=-1, j=0)
924 for counterop, numberop in [
925 (Counter.__add__, lambda x, y: max(0, x+y)),
926 (Counter.__sub__, lambda x, y: max(0, x-y)),
927 (Counter.__or__, lambda x, y: max(0,x,y)),
928 (Counter.__and__, lambda x, y: max(0, min(x,y))),
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000929 ]:
930 result = counterop(p, q)
931 for x in elements:
Raymond Hettingere0d1b9f2009-01-21 20:36:27 +0000932 self.assertEqual(numberop(p[x], q[x]), result[x],
933 (counterop, x, p, q))
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000934 # verify that results exclude non-positive counts
Benjamin Petersonc9c0f202009-06-30 23:06:06 +0000935 self.assertTrue(x>0 for x in result.values())
Raymond Hettinger4d2073a2009-01-20 03:41:22 +0000936
937 elements = 'abcdef'
938 for i in range(100):
939 # verify that random multisets with no repeats are exactly like sets
940 p = Counter(dict((elem, randrange(0, 2)) for elem in elements))
941 q = Counter(dict((elem, randrange(0, 2)) for elem in elements))
942 for counterop, setop in [
943 (Counter.__sub__, set.__sub__),
944 (Counter.__or__, set.__or__),
945 (Counter.__and__, set.__and__),
946 ]:
947 counter_result = counterop(p, q)
948 set_result = setop(set(p.elements()), set(q.elements()))
949 self.assertEqual(counter_result, dict.fromkeys(set_result, 1))
Raymond Hettingerb8baf632009-01-14 02:20:07 +0000950
Raymond Hettinger9c01e442010-04-03 10:32:58 +0000951 def test_subtract(self):
952 c = Counter(a=-5, b=0, c=5, d=10, e=15,g=40)
953 c.subtract(a=1, b=2, c=-3, d=10, e=20, f=30, h=-50)
954 self.assertEqual(c, Counter(a=-6, b=-2, c=8, d=0, e=-5, f=-30, g=40, h=50))
955 c = Counter(a=-5, b=0, c=5, d=10, e=15,g=40)
956 c.subtract(Counter(a=1, b=2, c=-3, d=10, e=20, f=30, h=-50))
957 self.assertEqual(c, Counter(a=-6, b=-2, c=8, d=0, e=-5, f=-30, g=40, h=50))
958 c = Counter('aaabbcd')
959 c.subtract('aaaabbcce')
960 self.assertEqual(c, Counter(a=-1, b=0, c=-1, d=1, e=-1))
Raymond Hettinger2d32f632009-03-02 21:24:57 +0000961
Raymond Hettinger426e0522011-01-03 02:12:02 +0000962 def test_helper_function(self):
963 # two paths, one for real dicts and one for other mappings
964 elems = list('abracadabra')
965
966 d = dict()
967 _count_elements(d, elems)
968 self.assertEqual(d, {'a': 5, 'r': 2, 'b': 2, 'c': 1, 'd': 1})
969
970 m = OrderedDict()
971 _count_elements(m, elems)
972 self.assertEqual(m,
973 OrderedDict([('a', 5), ('b', 2), ('r', 2), ('c', 1), ('d', 1)]))
974
Raymond Hettinger499e1932011-02-23 07:56:53 +0000975
976################################################################################
977### OrderedDict
978################################################################################
979
Raymond Hettinger2d32f632009-03-02 21:24:57 +0000980class TestOrderedDict(unittest.TestCase):
981
982 def test_init(self):
983 with self.assertRaises(TypeError):
984 OrderedDict([('a', 1), ('b', 2)], None) # too many args
985 pairs = [('a', 1), ('b', 2), ('c', 3), ('d', 4), ('e', 5)]
986 self.assertEqual(sorted(OrderedDict(dict(pairs)).items()), pairs) # dict input
987 self.assertEqual(sorted(OrderedDict(**dict(pairs)).items()), pairs) # kwds input
988 self.assertEqual(list(OrderedDict(pairs).items()), pairs) # pairs input
989 self.assertEqual(list(OrderedDict([('a', 1), ('b', 2), ('c', 9), ('d', 4)],
990 c=3, e=5).items()), pairs) # mixed input
991
992 # make sure no positional args conflict with possible kwdargs
993 self.assertEqual(inspect.getargspec(OrderedDict.__dict__['__init__']).args,
994 ['self'])
995
996 # Make sure that direct calls to __init__ do not clear previous contents
997 d = OrderedDict([('a', 1), ('b', 2), ('c', 3), ('d', 44), ('e', 55)])
998 d.__init__([('e', 5), ('f', 6)], g=7, d=4)
999 self.assertEqual(list(d.items()),
1000 [('a', 1), ('b', 2), ('c', 3), ('d', 4), ('e', 5), ('f', 6), ('g', 7)])
1001
1002 def test_update(self):
1003 with self.assertRaises(TypeError):
1004 OrderedDict().update([('a', 1), ('b', 2)], None) # too many args
1005 pairs = [('a', 1), ('b', 2), ('c', 3), ('d', 4), ('e', 5)]
1006 od = OrderedDict()
1007 od.update(dict(pairs))
1008 self.assertEqual(sorted(od.items()), pairs) # dict input
1009 od = OrderedDict()
1010 od.update(**dict(pairs))
1011 self.assertEqual(sorted(od.items()), pairs) # kwds input
1012 od = OrderedDict()
1013 od.update(pairs)
1014 self.assertEqual(list(od.items()), pairs) # pairs input
1015 od = OrderedDict()
1016 od.update([('a', 1), ('b', 2), ('c', 9), ('d', 4)], c=3, e=5)
1017 self.assertEqual(list(od.items()), pairs) # mixed input
1018
Mark Dickinsonb214e902010-07-11 18:53:06 +00001019 # Issue 9137: Named argument called 'other' or 'self'
1020 # shouldn't be treated specially.
1021 od = OrderedDict()
1022 od.update(self=23)
1023 self.assertEqual(list(od.items()), [('self', 23)])
1024 od = OrderedDict()
1025 od.update(other={})
1026 self.assertEqual(list(od.items()), [('other', {})])
1027 od = OrderedDict()
1028 od.update(red=5, blue=6, other=7, self=8)
1029 self.assertEqual(sorted(list(od.items())),
1030 [('blue', 6), ('other', 7), ('red', 5), ('self', 8)])
1031
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001032 # Make sure that direct calls to update do not clear previous contents
1033 # add that updates items are not moved to the end
1034 d = OrderedDict([('a', 1), ('b', 2), ('c', 3), ('d', 44), ('e', 55)])
1035 d.update([('e', 5), ('f', 6)], g=7, d=4)
1036 self.assertEqual(list(d.items()),
1037 [('a', 1), ('b', 2), ('c', 3), ('d', 4), ('e', 5), ('f', 6), ('g', 7)])
1038
Raymond Hettinger345c49b2011-01-01 23:51:55 +00001039 def test_abc(self):
1040 self.assertIsInstance(OrderedDict(), MutableMapping)
1041 self.assertTrue(issubclass(OrderedDict, MutableMapping))
1042
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001043 def test_clear(self):
1044 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1045 shuffle(pairs)
1046 od = OrderedDict(pairs)
1047 self.assertEqual(len(od), len(pairs))
1048 od.clear()
1049 self.assertEqual(len(od), 0)
1050
1051 def test_delitem(self):
1052 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1053 od = OrderedDict(pairs)
1054 del od['a']
Benjamin Peterson577473f2010-01-19 00:09:57 +00001055 self.assertNotIn('a', od)
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001056 with self.assertRaises(KeyError):
1057 del od['a']
1058 self.assertEqual(list(od.items()), pairs[:2] + pairs[3:])
1059
1060 def test_setitem(self):
1061 od = OrderedDict([('d', 1), ('b', 2), ('c', 3), ('a', 4), ('e', 5)])
1062 od['c'] = 10 # existing element
1063 od['f'] = 20 # new element
1064 self.assertEqual(list(od.items()),
1065 [('d', 1), ('b', 2), ('c', 10), ('a', 4), ('e', 5), ('f', 20)])
1066
1067 def test_iterators(self):
1068 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1069 shuffle(pairs)
1070 od = OrderedDict(pairs)
1071 self.assertEqual(list(od), [t[0] for t in pairs])
1072 self.assertEqual(list(od.keys()), [t[0] for t in pairs])
1073 self.assertEqual(list(od.values()), [t[1] for t in pairs])
1074 self.assertEqual(list(od.items()), pairs)
1075 self.assertEqual(list(reversed(od)),
1076 [t[0] for t in reversed(pairs)])
1077
1078 def test_popitem(self):
1079 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1080 shuffle(pairs)
1081 od = OrderedDict(pairs)
1082 while pairs:
1083 self.assertEqual(od.popitem(), pairs.pop())
1084 with self.assertRaises(KeyError):
1085 od.popitem()
1086 self.assertEqual(len(od), 0)
1087
1088 def test_pop(self):
1089 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1090 shuffle(pairs)
1091 od = OrderedDict(pairs)
1092 shuffle(pairs)
1093 while pairs:
1094 k, v = pairs.pop()
1095 self.assertEqual(od.pop(k), v)
1096 with self.assertRaises(KeyError):
1097 od.pop('xyz')
1098 self.assertEqual(len(od), 0)
1099 self.assertEqual(od.pop(k, 12345), 12345)
1100
Raymond Hettinger345c49b2011-01-01 23:51:55 +00001101 # make sure pop still works when __missing__ is defined
1102 class Missing(OrderedDict):
1103 def __missing__(self, key):
1104 return 0
1105 m = Missing(a=1)
1106 self.assertEqual(m.pop('b', 5), 5)
1107 self.assertEqual(m.pop('a', 6), 1)
1108 self.assertEqual(m.pop('a', 6), 6)
1109 with self.assertRaises(KeyError):
1110 m.pop('a')
1111
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001112 def test_equality(self):
1113 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1114 shuffle(pairs)
1115 od1 = OrderedDict(pairs)
1116 od2 = OrderedDict(pairs)
1117 self.assertEqual(od1, od2) # same order implies equality
1118 pairs = pairs[2:] + pairs[:2]
1119 od2 = OrderedDict(pairs)
1120 self.assertNotEqual(od1, od2) # different order implies inequality
1121 # comparison to regular dict is not order sensitive
1122 self.assertEqual(od1, dict(od2))
1123 self.assertEqual(dict(od2), od1)
1124 # different length implied inequality
1125 self.assertNotEqual(od1, OrderedDict(pairs[:-1]))
1126
1127 def test_copying(self):
1128 # Check that ordered dicts are copyable, deepcopyable, picklable,
1129 # and have a repr/eval round-trip
1130 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1131 od = OrderedDict(pairs)
1132 update_test = OrderedDict()
1133 update_test.update(od)
1134 for i, dup in enumerate([
1135 od.copy(),
1136 copy.copy(od),
1137 copy.deepcopy(od),
1138 pickle.loads(pickle.dumps(od, 0)),
1139 pickle.loads(pickle.dumps(od, 1)),
1140 pickle.loads(pickle.dumps(od, 2)),
1141 pickle.loads(pickle.dumps(od, 3)),
1142 pickle.loads(pickle.dumps(od, -1)),
1143 eval(repr(od)),
1144 update_test,
1145 OrderedDict(od),
1146 ]):
Benjamin Petersonc9c0f202009-06-30 23:06:06 +00001147 self.assertTrue(dup is not od)
Ezio Melottib3aedd42010-11-20 19:04:17 +00001148 self.assertEqual(dup, od)
1149 self.assertEqual(list(dup.items()), list(od.items()))
1150 self.assertEqual(len(dup), len(od))
1151 self.assertEqual(type(dup), type(od))
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001152
Raymond Hettinger5b26fb52009-03-03 22:38:22 +00001153 def test_yaml_linkage(self):
1154 # Verify that __reduce__ is setup in a way that supports PyYAML's dump() feature.
1155 # In yaml, lists are native but tuples are not.
1156 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1157 od = OrderedDict(pairs)
1158 # yaml.dump(od) -->
1159 # '!!python/object/apply:__main__.OrderedDict\n- - [a, 1]\n - [b, 2]\n'
Benjamin Petersonc9c0f202009-06-30 23:06:06 +00001160 self.assertTrue(all(type(pair)==list for pair in od.__reduce__()[1]))
Raymond Hettinger5b26fb52009-03-03 22:38:22 +00001161
Raymond Hettingerb2121572009-03-03 22:50:04 +00001162 def test_reduce_not_too_fat(self):
1163 # do not save instance dictionary if not needed
1164 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1165 od = OrderedDict(pairs)
1166 self.assertEqual(len(od.__reduce__()), 2)
1167 od.x = 10
1168 self.assertEqual(len(od.__reduce__()), 3)
1169
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001170 def test_repr(self):
1171 od = OrderedDict([('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)])
1172 self.assertEqual(repr(od),
1173 "OrderedDict([('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)])")
1174 self.assertEqual(eval(repr(od)), od)
1175 self.assertEqual(repr(OrderedDict()), "OrderedDict()")
1176
Raymond Hettingerdc08a142010-09-12 05:15:22 +00001177 def test_repr_recursive(self):
1178 # See issue #9826
1179 od = OrderedDict.fromkeys('abc')
1180 od['x'] = od
1181 self.assertEqual(repr(od),
1182 "OrderedDict([('a', None), ('b', None), ('c', None), ('x', ...)])")
1183
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001184 def test_setdefault(self):
1185 pairs = [('c', 1), ('b', 2), ('a', 3), ('d', 4), ('e', 5), ('f', 6)]
1186 shuffle(pairs)
1187 od = OrderedDict(pairs)
1188 pair_order = list(od.items())
1189 self.assertEqual(od.setdefault('a', 10), 3)
1190 # make sure order didn't change
1191 self.assertEqual(list(od.items()), pair_order)
1192 self.assertEqual(od.setdefault('x', 10), 10)
1193 # make sure 'x' is added to the end
1194 self.assertEqual(list(od.items())[-1], ('x', 10))
1195
Raymond Hettingera673b1f2010-12-31 23:16:17 +00001196 # make sure setdefault still works when __missing__ is defined
1197 class Missing(OrderedDict):
1198 def __missing__(self, key):
1199 return 0
1200 self.assertEqual(Missing().setdefault(5, 9), 9)
1201
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001202 def test_reinsert(self):
1203 # Given insert a, insert b, delete a, re-insert a,
1204 # verify that a is now later than b.
1205 od = OrderedDict()
1206 od['a'] = 1
1207 od['b'] = 2
1208 del od['a']
1209 od['a'] = 1
1210 self.assertEqual(list(od.items()), [('b', 2), ('a', 1)])
1211
Raymond Hettingerf45abc92010-09-06 21:26:09 +00001212 def test_move_to_end(self):
1213 od = OrderedDict.fromkeys('abcde')
1214 self.assertEqual(list(od), list('abcde'))
1215 od.move_to_end('c')
1216 self.assertEqual(list(od), list('abdec'))
1217 od.move_to_end('c', 0)
1218 self.assertEqual(list(od), list('cabde'))
1219 od.move_to_end('c', 0)
1220 self.assertEqual(list(od), list('cabde'))
1221 od.move_to_end('e')
1222 self.assertEqual(list(od), list('cabde'))
1223 with self.assertRaises(KeyError):
1224 od.move_to_end('x')
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001225
Raymond Hettinger35c87f22010-09-16 19:10:17 +00001226 def test_sizeof(self):
1227 # Wimpy test: Just verify the reported size is larger than a regular dict
1228 d = dict(a=1)
1229 od = OrderedDict(**d)
1230 self.assertGreater(sys.getsizeof(od), sys.getsizeof(d))
1231
Raymond Hettinger32062e92011-01-01 22:38:00 +00001232 def test_override_update(self):
1233 # Verify that subclasses can override update() without breaking __init__()
1234 class MyOD(OrderedDict):
1235 def update(self, *args, **kwds):
1236 raise Exception()
1237 items = [('a', 1), ('c', 3), ('b', 2)]
1238 self.assertEqual(list(MyOD(items).items()), items)
1239
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001240class GeneralMappingTests(mapping_tests.BasicTestMappingProtocol):
1241 type2test = OrderedDict
1242
Raymond Hettingerdc879f02009-03-19 20:30:56 +00001243 def test_popitem(self):
1244 d = self._empty_mapping()
1245 self.assertRaises(KeyError, d.popitem)
1246
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001247class MyOrderedDict(OrderedDict):
1248 pass
1249
1250class SubclassMappingTests(mapping_tests.BasicTestMappingProtocol):
1251 type2test = MyOrderedDict
1252
Raymond Hettingerdc879f02009-03-19 20:30:56 +00001253 def test_popitem(self):
1254 d = self._empty_mapping()
1255 self.assertRaises(KeyError, d.popitem)
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001256
1257
Raymond Hettinger499e1932011-02-23 07:56:53 +00001258################################################################################
1259### Run tests
1260################################################################################
1261
Christian Heimes25bb7832008-01-11 16:17:00 +00001262import doctest, collections
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001263
Guido van Rossumd8faa362007-04-27 19:54:29 +00001264def test_main(verbose=None):
Benjamin Petersonad9d48d2008-04-02 21:49:44 +00001265 NamedTupleDocs = doctest.DocTestSuite(module=collections)
Raymond Hettingerb8baf632009-01-14 02:20:07 +00001266 test_classes = [TestNamedTuple, NamedTupleDocs, TestOneTrickPonyABCs,
Raymond Hettingerd0321312011-02-26 06:53:58 +00001267 TestCollectionABCs, TestCounter, TestChainMap,
Raymond Hettinger2d32f632009-03-02 21:24:57 +00001268 TestOrderedDict, GeneralMappingTests, SubclassMappingTests]
Benjamin Petersonee8712c2008-05-20 21:35:26 +00001269 support.run_unittest(*test_classes)
1270 support.run_doctest(collections, verbose)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001271
Guido van Rossumcd16bf62007-06-13 18:07:49 +00001272
Guido van Rossumd8faa362007-04-27 19:54:29 +00001273if __name__ == "__main__":
1274 test_main(verbose=True)