python (3.12.0)
1 '''This module implements specialized container datatypes providing
2 alternatives to Python's general purpose built-in containers, dict,
3 list, set, and tuple.
4
5 * namedtuple factory function for creating tuple subclasses with named fields
6 * deque list-like container with fast appends and pops on either end
7 * ChainMap dict-like class for creating a single view of multiple mappings
8 * Counter dict subclass for counting hashable objects
9 * OrderedDict dict subclass that remembers the order entries were added
10 * defaultdict dict subclass that calls a factory function to supply missing values
11 * UserDict wrapper around dictionary objects for easier dict subclassing
12 * UserList wrapper around list objects for easier list subclassing
13 * UserString wrapper around string objects for easier string subclassing
14
15 '''
16
17 __all__ = [
18 'ChainMap',
19 'Counter',
20 'OrderedDict',
21 'UserDict',
22 'UserList',
23 'UserString',
24 'defaultdict',
25 'deque',
26 'namedtuple',
27 ]
28
29 import _collections_abc
30 import sys as _sys
31
32 from itertools import chain as _chain
33 from itertools import repeat as _repeat
34 from itertools import starmap as _starmap
35 from keyword import iskeyword as _iskeyword
36 from operator import eq as _eq
37 from operator import itemgetter as _itemgetter
38 from reprlib import recursive_repr as _recursive_repr
39 from _weakref import proxy as _proxy
40
41 try:
42 from _collections import deque
43 except ImportError:
44 pass
45 else:
46 _collections_abc.MutableSequence.register(deque)
47
48 try:
49 from _collections import _deque_iterator
50 except ImportError:
51 pass
52
53 try:
54 from _collections import defaultdict
55 except ImportError:
56 pass
57
58
59 ################################################################################
60 ### OrderedDict
61 ################################################################################
62
63 class ESC[4;38;5;81m_OrderedDictKeysView(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mKeysView):
64
65 def __reversed__(self):
66 yield from reversed(self._mapping)
67
68 class ESC[4;38;5;81m_OrderedDictItemsView(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mItemsView):
69
70 def __reversed__(self):
71 for key in reversed(self._mapping):
72 yield (key, self._mapping[key])
73
74 class ESC[4;38;5;81m_OrderedDictValuesView(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mValuesView):
75
76 def __reversed__(self):
77 for key in reversed(self._mapping):
78 yield self._mapping[key]
79
80 class ESC[4;38;5;81m_Link(ESC[4;38;5;149mobject):
81 __slots__ = 'prev', 'next', 'key', '__weakref__'
82
83 class ESC[4;38;5;81mOrderedDict(ESC[4;38;5;149mdict):
84 'Dictionary that remembers insertion order'
85 # An inherited dict maps keys to values.
86 # The inherited dict provides __getitem__, __len__, __contains__, and get.
87 # The remaining methods are order-aware.
88 # Big-O running times for all methods are the same as regular dictionaries.
89
90 # The internal self.__map dict maps keys to links in a doubly linked list.
91 # The circular doubly linked list starts and ends with a sentinel element.
92 # The sentinel element never gets deleted (this simplifies the algorithm).
93 # The sentinel is in self.__hardroot with a weakref proxy in self.__root.
94 # The prev links are weakref proxies (to prevent circular references).
95 # Individual links are kept alive by the hard reference in self.__map.
96 # Those hard references disappear when a key is deleted from an OrderedDict.
97
98 def __new__(cls, /, *args, **kwds):
99 "Create the ordered dict object and set up the underlying structures."
100 self = dict.__new__(cls)
101 self.__hardroot = _Link()
102 self.__root = root = _proxy(self.__hardroot)
103 root.prev = root.next = root
104 self.__map = {}
105 return self
106
107 def __init__(self, other=(), /, **kwds):
108 '''Initialize an ordered dictionary. The signature is the same as
109 regular dictionaries. Keyword argument order is preserved.
110 '''
111 self.__update(other, **kwds)
112
113 def __setitem__(self, key, value,
114 dict_setitem=dict.__setitem__, proxy=_proxy, Link=_Link):
115 'od.__setitem__(i, y) <==> od[i]=y'
116 # Setting a new item creates a new link at the end of the linked list,
117 # and the inherited dictionary is updated with the new key/value pair.
118 if key not in self:
119 self.__map[key] = link = Link()
120 root = self.__root
121 last = root.prev
122 link.prev, link.next, link.key = last, root, key
123 last.next = link
124 root.prev = proxy(link)
125 dict_setitem(self, key, value)
126
127 def __delitem__(self, key, dict_delitem=dict.__delitem__):
128 'od.__delitem__(y) <==> del od[y]'
129 # Deleting an existing item uses self.__map to find the link which gets
130 # removed by updating the links in the predecessor and successor nodes.
131 dict_delitem(self, key)
132 link = self.__map.pop(key)
133 link_prev = link.prev
134 link_next = link.next
135 link_prev.next = link_next
136 link_next.prev = link_prev
137 link.prev = None
138 link.next = None
139
140 def __iter__(self):
141 'od.__iter__() <==> iter(od)'
142 # Traverse the linked list in order.
143 root = self.__root
144 curr = root.next
145 while curr is not root:
146 yield curr.key
147 curr = curr.next
148
149 def __reversed__(self):
150 'od.__reversed__() <==> reversed(od)'
151 # Traverse the linked list in reverse order.
152 root = self.__root
153 curr = root.prev
154 while curr is not root:
155 yield curr.key
156 curr = curr.prev
157
158 def clear(self):
159 'od.clear() -> None. Remove all items from od.'
160 root = self.__root
161 root.prev = root.next = root
162 self.__map.clear()
163 dict.clear(self)
164
165 def popitem(self, last=True):
166 '''Remove and return a (key, value) pair from the dictionary.
167
168 Pairs are returned in LIFO order if last is true or FIFO order if false.
169 '''
170 if not self:
171 raise KeyError('dictionary is empty')
172 root = self.__root
173 if last:
174 link = root.prev
175 link_prev = link.prev
176 link_prev.next = root
177 root.prev = link_prev
178 else:
179 link = root.next
180 link_next = link.next
181 root.next = link_next
182 link_next.prev = root
183 key = link.key
184 del self.__map[key]
185 value = dict.pop(self, key)
186 return key, value
187
188 def move_to_end(self, key, last=True):
189 '''Move an existing element to the end (or beginning if last is false).
190
191 Raise KeyError if the element does not exist.
192 '''
193 link = self.__map[key]
194 link_prev = link.prev
195 link_next = link.next
196 soft_link = link_next.prev
197 link_prev.next = link_next
198 link_next.prev = link_prev
199 root = self.__root
200 if last:
201 last = root.prev
202 link.prev = last
203 link.next = root
204 root.prev = soft_link
205 last.next = link
206 else:
207 first = root.next
208 link.prev = root
209 link.next = first
210 first.prev = soft_link
211 root.next = link
212
213 def __sizeof__(self):
214 sizeof = _sys.getsizeof
215 n = len(self) + 1 # number of links including root
216 size = sizeof(self.__dict__) # instance dictionary
217 size += sizeof(self.__map) * 2 # internal dict and inherited dict
218 size += sizeof(self.__hardroot) * n # link objects
219 size += sizeof(self.__root) * n # proxy objects
220 return size
221
222 update = __update = _collections_abc.MutableMapping.update
223
224 def keys(self):
225 "D.keys() -> a set-like object providing a view on D's keys"
226 return _OrderedDictKeysView(self)
227
228 def items(self):
229 "D.items() -> a set-like object providing a view on D's items"
230 return _OrderedDictItemsView(self)
231
232 def values(self):
233 "D.values() -> an object providing a view on D's values"
234 return _OrderedDictValuesView(self)
235
236 __ne__ = _collections_abc.MutableMapping.__ne__
237
238 __marker = object()
239
240 def pop(self, key, default=__marker):
241 '''od.pop(k[,d]) -> v, remove specified key and return the corresponding
242 value. If key is not found, d is returned if given, otherwise KeyError
243 is raised.
244
245 '''
246 marker = self.__marker
247 result = dict.pop(self, key, marker)
248 if result is not marker:
249 # The same as in __delitem__().
250 link = self.__map.pop(key)
251 link_prev = link.prev
252 link_next = link.next
253 link_prev.next = link_next
254 link_next.prev = link_prev
255 link.prev = None
256 link.next = None
257 return result
258 if default is marker:
259 raise KeyError(key)
260 return default
261
262 def setdefault(self, key, default=None):
263 '''Insert key with a value of default if key is not in the dictionary.
264
265 Return the value for key if key is in the dictionary, else default.
266 '''
267 if key in self:
268 return self[key]
269 self[key] = default
270 return default
271
272 @_recursive_repr()
273 def __repr__(self):
274 'od.__repr__() <==> repr(od)'
275 if not self:
276 return '%s()' % (self.__class__.__name__,)
277 return '%s(%r)' % (self.__class__.__name__, dict(self.items()))
278
279 def __reduce__(self):
280 'Return state information for pickling'
281 state = self.__getstate__()
282 if state:
283 if isinstance(state, tuple):
284 state, slots = state
285 else:
286 slots = {}
287 state = state.copy()
288 slots = slots.copy()
289 for k in vars(OrderedDict()):
290 state.pop(k, None)
291 slots.pop(k, None)
292 if slots:
293 state = state, slots
294 else:
295 state = state or None
296 return self.__class__, (), state, None, iter(self.items())
297
298 def copy(self):
299 'od.copy() -> a shallow copy of od'
300 return self.__class__(self)
301
302 @classmethod
303 def fromkeys(cls, iterable, value=None):
304 '''Create a new ordered dictionary with keys from iterable and values set to value.
305 '''
306 self = cls()
307 for key in iterable:
308 self[key] = value
309 return self
310
311 def __eq__(self, other):
312 '''od.__eq__(y) <==> od==y. Comparison to another OD is order-sensitive
313 while comparison to a regular mapping is order-insensitive.
314
315 '''
316 if isinstance(other, OrderedDict):
317 return dict.__eq__(self, other) and all(map(_eq, self, other))
318 return dict.__eq__(self, other)
319
320 def __ior__(self, other):
321 self.update(other)
322 return self
323
324 def __or__(self, other):
325 if not isinstance(other, dict):
326 return NotImplemented
327 new = self.__class__(self)
328 new.update(other)
329 return new
330
331 def __ror__(self, other):
332 if not isinstance(other, dict):
333 return NotImplemented
334 new = self.__class__(other)
335 new.update(self)
336 return new
337
338
339 try:
340 from _collections import OrderedDict
341 except ImportError:
342 # Leave the pure Python version in place.
343 pass
344
345
346 ################################################################################
347 ### namedtuple
348 ################################################################################
349
350 try:
351 from _collections import _tuplegetter
352 except ImportError:
353 _tuplegetter = lambda index, doc: property(_itemgetter(index), doc=doc)
354
355 def namedtuple(typename, field_names, *, rename=False, defaults=None, module=None):
356 """Returns a new subclass of tuple with named fields.
357
358 >>> Point = namedtuple('Point', ['x', 'y'])
359 >>> Point.__doc__ # docstring for the new class
360 'Point(x, y)'
361 >>> p = Point(11, y=22) # instantiate with positional args or keywords
362 >>> p[0] + p[1] # indexable like a plain tuple
363 33
364 >>> x, y = p # unpack like a regular tuple
365 >>> x, y
366 (11, 22)
367 >>> p.x + p.y # fields also accessible by name
368 33
369 >>> d = p._asdict() # convert to a dictionary
370 >>> d['x']
371 11
372 >>> Point(**d) # convert from a dictionary
373 Point(x=11, y=22)
374 >>> p._replace(x=100) # _replace() is like str.replace() but targets named fields
375 Point(x=100, y=22)
376
377 """
378
379 # Validate the field names. At the user's option, either generate an error
380 # message or automatically replace the field name with a valid name.
381 if isinstance(field_names, str):
382 field_names = field_names.replace(',', ' ').split()
383 field_names = list(map(str, field_names))
384 typename = _sys.intern(str(typename))
385
386 if rename:
387 seen = set()
388 for index, name in enumerate(field_names):
389 if (not name.isidentifier()
390 or _iskeyword(name)
391 or name.startswith('_')
392 or name in seen):
393 field_names[index] = f'_{index}'
394 seen.add(name)
395
396 for name in [typename] + field_names:
397 if type(name) is not str:
398 raise TypeError('Type names and field names must be strings')
399 if not name.isidentifier():
400 raise ValueError('Type names and field names must be valid '
401 f'identifiers: {name!r}')
402 if _iskeyword(name):
403 raise ValueError('Type names and field names cannot be a '
404 f'keyword: {name!r}')
405
406 seen = set()
407 for name in field_names:
408 if name.startswith('_') and not rename:
409 raise ValueError('Field names cannot start with an underscore: '
410 f'{name!r}')
411 if name in seen:
412 raise ValueError(f'Encountered duplicate field name: {name!r}')
413 seen.add(name)
414
415 field_defaults = {}
416 if defaults is not None:
417 defaults = tuple(defaults)
418 if len(defaults) > len(field_names):
419 raise TypeError('Got more default values than field names')
420 field_defaults = dict(reversed(list(zip(reversed(field_names),
421 reversed(defaults)))))
422
423 # Variables used in the methods and docstrings
424 field_names = tuple(map(_sys.intern, field_names))
425 num_fields = len(field_names)
426 arg_list = ', '.join(field_names)
427 if num_fields == 1:
428 arg_list += ','
429 repr_fmt = '(' + ', '.join(f'{name}=%r' for name in field_names) + ')'
430 tuple_new = tuple.__new__
431 _dict, _tuple, _len, _map, _zip = dict, tuple, len, map, zip
432
433 # Create all the named tuple methods to be added to the class namespace
434
435 namespace = {
436 '_tuple_new': tuple_new,
437 '__builtins__': {},
438 '__name__': f'namedtuple_{typename}',
439 }
440 code = f'lambda _cls, {arg_list}: _tuple_new(_cls, ({arg_list}))'
441 __new__ = eval(code, namespace)
442 __new__.__name__ = '__new__'
443 __new__.__doc__ = f'Create new instance of {typename}({arg_list})'
444 if defaults is not None:
445 __new__.__defaults__ = defaults
446
447 @classmethod
448 def _make(cls, iterable):
449 result = tuple_new(cls, iterable)
450 if _len(result) != num_fields:
451 raise TypeError(f'Expected {num_fields} arguments, got {len(result)}')
452 return result
453
454 _make.__func__.__doc__ = (f'Make a new {typename} object from a sequence '
455 'or iterable')
456
457 def _replace(self, /, **kwds):
458 result = self._make(_map(kwds.pop, field_names, self))
459 if kwds:
460 raise ValueError(f'Got unexpected field names: {list(kwds)!r}')
461 return result
462
463 _replace.__doc__ = (f'Return a new {typename} object replacing specified '
464 'fields with new values')
465
466 def __repr__(self):
467 'Return a nicely formatted representation string'
468 return self.__class__.__name__ + repr_fmt % self
469
470 def _asdict(self):
471 'Return a new dict which maps field names to their values.'
472 return _dict(_zip(self._fields, self))
473
474 def __getnewargs__(self):
475 'Return self as a plain tuple. Used by copy and pickle.'
476 return _tuple(self)
477
478 # Modify function metadata to help with introspection and debugging
479 for method in (
480 __new__,
481 _make.__func__,
482 _replace,
483 __repr__,
484 _asdict,
485 __getnewargs__,
486 ):
487 method.__qualname__ = f'{typename}.{method.__name__}'
488
489 # Build-up the class namespace dictionary
490 # and use type() to build the result class
491 class_namespace = {
492 '__doc__': f'{typename}({arg_list})',
493 '__slots__': (),
494 '_fields': field_names,
495 '_field_defaults': field_defaults,
496 '__new__': __new__,
497 '_make': _make,
498 '_replace': _replace,
499 '__repr__': __repr__,
500 '_asdict': _asdict,
501 '__getnewargs__': __getnewargs__,
502 '__match_args__': field_names,
503 }
504 for index, name in enumerate(field_names):
505 doc = _sys.intern(f'Alias for field number {index}')
506 class_namespace[name] = _tuplegetter(index, doc)
507
508 result = type(typename, (tuple,), class_namespace)
509
510 # For pickling to work, the __module__ variable needs to be set to the frame
511 # where the named tuple is created. Bypass this step in environments where
512 # sys._getframe is not defined (Jython for example) or sys._getframe is not
513 # defined for arguments greater than 0 (IronPython), or where the user has
514 # specified a particular module.
515 if module is None:
516 try:
517 module = _sys._getframemodulename(1) or '__main__'
518 except AttributeError:
519 try:
520 module = _sys._getframe(1).f_globals.get('__name__', '__main__')
521 except (AttributeError, ValueError):
522 pass
523 if module is not None:
524 result.__module__ = module
525
526 return result
527
528
529 ########################################################################
530 ### Counter
531 ########################################################################
532
533 def _count_elements(mapping, iterable):
534 'Tally elements from the iterable.'
535 mapping_get = mapping.get
536 for elem in iterable:
537 mapping[elem] = mapping_get(elem, 0) + 1
538
539 try: # Load C helper function if available
540 from _collections import _count_elements
541 except ImportError:
542 pass
543
544 class ESC[4;38;5;81mCounter(ESC[4;38;5;149mdict):
545 '''Dict subclass for counting hashable items. Sometimes called a bag
546 or multiset. Elements are stored as dictionary keys and their counts
547 are stored as dictionary values.
548
549 >>> c = Counter('abcdeabcdabcaba') # count elements from a string
550
551 >>> c.most_common(3) # three most common elements
552 [('a', 5), ('b', 4), ('c', 3)]
553 >>> sorted(c) # list all unique elements
554 ['a', 'b', 'c', 'd', 'e']
555 >>> ''.join(sorted(c.elements())) # list elements with repetitions
556 'aaaaabbbbcccdde'
557 >>> sum(c.values()) # total of all counts
558 15
559
560 >>> c['a'] # count of letter 'a'
561 5
562 >>> for elem in 'shazam': # update counts from an iterable
563 ... c[elem] += 1 # by adding 1 to each element's count
564 >>> c['a'] # now there are seven 'a'
565 7
566 >>> del c['b'] # remove all 'b'
567 >>> c['b'] # now there are zero 'b'
568 0
569
570 >>> d = Counter('simsalabim') # make another counter
571 >>> c.update(d) # add in the second counter
572 >>> c['a'] # now there are nine 'a'
573 9
574
575 >>> c.clear() # empty the counter
576 >>> c
577 Counter()
578
579 Note: If a count is set to zero or reduced to zero, it will remain
580 in the counter until the entry is deleted or the counter is cleared:
581
582 >>> c = Counter('aaabbc')
583 >>> c['b'] -= 2 # reduce the count of 'b' by two
584 >>> c.most_common() # 'b' is still in, but its count is zero
585 [('a', 3), ('c', 1), ('b', 0)]
586
587 '''
588 # References:
589 # http://en.wikipedia.org/wiki/Multiset
590 # http://www.gnu.org/software/smalltalk/manual-base/html_node/Bag.html
591 # http://www.demo2s.com/Tutorial/Cpp/0380__set-multiset/Catalog0380__set-multiset.htm
592 # http://code.activestate.com/recipes/259174/
593 # Knuth, TAOCP Vol. II section 4.6.3
594
595 def __init__(self, iterable=None, /, **kwds):
596 '''Create a new, empty Counter object. And if given, count elements
597 from an input iterable. Or, initialize the count from another mapping
598 of elements to their counts.
599
600 >>> c = Counter() # a new, empty counter
601 >>> c = Counter('gallahad') # a new counter from an iterable
602 >>> c = Counter({'a': 4, 'b': 2}) # a new counter from a mapping
603 >>> c = Counter(a=4, b=2) # a new counter from keyword args
604
605 '''
606 super().__init__()
607 self.update(iterable, **kwds)
608
609 def __missing__(self, key):
610 'The count of elements not in the Counter is zero.'
611 # Needed so that self[missing_item] does not raise KeyError
612 return 0
613
614 def total(self):
615 'Sum of the counts'
616 return sum(self.values())
617
618 def most_common(self, n=None):
619 '''List the n most common elements and their counts from the most
620 common to the least. If n is None, then list all element counts.
621
622 >>> Counter('abracadabra').most_common(3)
623 [('a', 5), ('b', 2), ('r', 2)]
624
625 '''
626 # Emulate Bag.sortedByCount from Smalltalk
627 if n is None:
628 return sorted(self.items(), key=_itemgetter(1), reverse=True)
629
630 # Lazy import to speedup Python startup time
631 import heapq
632 return heapq.nlargest(n, self.items(), key=_itemgetter(1))
633
634 def elements(self):
635 '''Iterator over elements repeating each as many times as its count.
636
637 >>> c = Counter('ABCABC')
638 >>> sorted(c.elements())
639 ['A', 'A', 'B', 'B', 'C', 'C']
640
641 # Knuth's example for prime factors of 1836: 2**2 * 3**3 * 17**1
642 >>> import math
643 >>> prime_factors = Counter({2: 2, 3: 3, 17: 1})
644 >>> math.prod(prime_factors.elements())
645 1836
646
647 Note, if an element's count has been set to zero or is a negative
648 number, elements() will ignore it.
649
650 '''
651 # Emulate Bag.do from Smalltalk and Multiset.begin from C++.
652 return _chain.from_iterable(_starmap(_repeat, self.items()))
653
654 # Override dict methods where necessary
655
656 @classmethod
657 def fromkeys(cls, iterable, v=None):
658 # There is no equivalent method for counters because the semantics
659 # would be ambiguous in cases such as Counter.fromkeys('aaabbc', v=2).
660 # Initializing counters to zero values isn't necessary because zero
661 # is already the default value for counter lookups. Initializing
662 # to one is easily accomplished with Counter(set(iterable)). For
663 # more exotic cases, create a dictionary first using a dictionary
664 # comprehension or dict.fromkeys().
665 raise NotImplementedError(
666 'Counter.fromkeys() is undefined. Use Counter(iterable) instead.')
667
668 def update(self, iterable=None, /, **kwds):
669 '''Like dict.update() but add counts instead of replacing them.
670
671 Source can be an iterable, a dictionary, or another Counter instance.
672
673 >>> c = Counter('which')
674 >>> c.update('witch') # add elements from another iterable
675 >>> d = Counter('watch')
676 >>> c.update(d) # add elements from another counter
677 >>> c['h'] # four 'h' in which, witch, and watch
678 4
679
680 '''
681 # The regular dict.update() operation makes no sense here because the
682 # replace behavior results in the some of original untouched counts
683 # being mixed-in with all of the other counts for a mismash that
684 # doesn't have a straight-forward interpretation in most counting
685 # contexts. Instead, we implement straight-addition. Both the inputs
686 # and outputs are allowed to contain zero and negative counts.
687
688 if iterable is not None:
689 if isinstance(iterable, _collections_abc.Mapping):
690 if self:
691 self_get = self.get
692 for elem, count in iterable.items():
693 self[elem] = count + self_get(elem, 0)
694 else:
695 # fast path when counter is empty
696 super().update(iterable)
697 else:
698 _count_elements(self, iterable)
699 if kwds:
700 self.update(kwds)
701
702 def subtract(self, iterable=None, /, **kwds):
703 '''Like dict.update() but subtracts counts instead of replacing them.
704 Counts can be reduced below zero. Both the inputs and outputs are
705 allowed to contain zero and negative counts.
706
707 Source can be an iterable, a dictionary, or another Counter instance.
708
709 >>> c = Counter('which')
710 >>> c.subtract('witch') # subtract elements from another iterable
711 >>> c.subtract(Counter('watch')) # subtract elements from another counter
712 >>> c['h'] # 2 in which, minus 1 in witch, minus 1 in watch
713 0
714 >>> c['w'] # 1 in which, minus 1 in witch, minus 1 in watch
715 -1
716
717 '''
718 if iterable is not None:
719 self_get = self.get
720 if isinstance(iterable, _collections_abc.Mapping):
721 for elem, count in iterable.items():
722 self[elem] = self_get(elem, 0) - count
723 else:
724 for elem in iterable:
725 self[elem] = self_get(elem, 0) - 1
726 if kwds:
727 self.subtract(kwds)
728
729 def copy(self):
730 'Return a shallow copy.'
731 return self.__class__(self)
732
733 def __reduce__(self):
734 return self.__class__, (dict(self),)
735
736 def __delitem__(self, elem):
737 'Like dict.__delitem__() but does not raise KeyError for missing values.'
738 if elem in self:
739 super().__delitem__(elem)
740
741 def __repr__(self):
742 if not self:
743 return f'{self.__class__.__name__}()'
744 try:
745 # dict() preserves the ordering returned by most_common()
746 d = dict(self.most_common())
747 except TypeError:
748 # handle case where values are not orderable
749 d = dict(self)
750 return f'{self.__class__.__name__}({d!r})'
751
752 # Multiset-style mathematical operations discussed in:
753 # Knuth TAOCP Volume II section 4.6.3 exercise 19
754 # and at http://en.wikipedia.org/wiki/Multiset
755 #
756 # Outputs guaranteed to only include positive counts.
757 #
758 # To strip negative and zero counts, add-in an empty counter:
759 # c += Counter()
760 #
761 # Results are ordered according to when an element is first
762 # encountered in the left operand and then by the order
763 # encountered in the right operand.
764 #
765 # When the multiplicities are all zero or one, multiset operations
766 # are guaranteed to be equivalent to the corresponding operations
767 # for regular sets.
768 # Given counter multisets such as:
769 # cp = Counter(a=1, b=0, c=1)
770 # cq = Counter(c=1, d=0, e=1)
771 # The corresponding regular sets would be:
772 # sp = {'a', 'c'}
773 # sq = {'c', 'e'}
774 # All of the following relations would hold:
775 # set(cp + cq) == sp | sq
776 # set(cp - cq) == sp - sq
777 # set(cp | cq) == sp | sq
778 # set(cp & cq) == sp & sq
779 # (cp == cq) == (sp == sq)
780 # (cp != cq) == (sp != sq)
781 # (cp <= cq) == (sp <= sq)
782 # (cp < cq) == (sp < sq)
783 # (cp >= cq) == (sp >= sq)
784 # (cp > cq) == (sp > sq)
785
786 def __eq__(self, other):
787 'True if all counts agree. Missing counts are treated as zero.'
788 if not isinstance(other, Counter):
789 return NotImplemented
790 return all(self[e] == other[e] for c in (self, other) for e in c)
791
792 def __ne__(self, other):
793 'True if any counts disagree. Missing counts are treated as zero.'
794 if not isinstance(other, Counter):
795 return NotImplemented
796 return not self == other
797
798 def __le__(self, other):
799 'True if all counts in self are a subset of those in other.'
800 if not isinstance(other, Counter):
801 return NotImplemented
802 return all(self[e] <= other[e] for c in (self, other) for e in c)
803
804 def __lt__(self, other):
805 'True if all counts in self are a proper subset of those in other.'
806 if not isinstance(other, Counter):
807 return NotImplemented
808 return self <= other and self != other
809
810 def __ge__(self, other):
811 'True if all counts in self are a superset of those in other.'
812 if not isinstance(other, Counter):
813 return NotImplemented
814 return all(self[e] >= other[e] for c in (self, other) for e in c)
815
816 def __gt__(self, other):
817 'True if all counts in self are a proper superset of those in other.'
818 if not isinstance(other, Counter):
819 return NotImplemented
820 return self >= other and self != other
821
822 def __add__(self, other):
823 '''Add counts from two counters.
824
825 >>> Counter('abbb') + Counter('bcc')
826 Counter({'b': 4, 'c': 2, 'a': 1})
827
828 '''
829 if not isinstance(other, Counter):
830 return NotImplemented
831 result = Counter()
832 for elem, count in self.items():
833 newcount = count + other[elem]
834 if newcount > 0:
835 result[elem] = newcount
836 for elem, count in other.items():
837 if elem not in self and count > 0:
838 result[elem] = count
839 return result
840
841 def __sub__(self, other):
842 ''' Subtract count, but keep only results with positive counts.
843
844 >>> Counter('abbbc') - Counter('bccd')
845 Counter({'b': 2, 'a': 1})
846
847 '''
848 if not isinstance(other, Counter):
849 return NotImplemented
850 result = Counter()
851 for elem, count in self.items():
852 newcount = count - other[elem]
853 if newcount > 0:
854 result[elem] = newcount
855 for elem, count in other.items():
856 if elem not in self and count < 0:
857 result[elem] = 0 - count
858 return result
859
860 def __or__(self, other):
861 '''Union is the maximum of value in either of the input counters.
862
863 >>> Counter('abbb') | Counter('bcc')
864 Counter({'b': 3, 'c': 2, 'a': 1})
865
866 '''
867 if not isinstance(other, Counter):
868 return NotImplemented
869 result = Counter()
870 for elem, count in self.items():
871 other_count = other[elem]
872 newcount = other_count if count < other_count else count
873 if newcount > 0:
874 result[elem] = newcount
875 for elem, count in other.items():
876 if elem not in self and count > 0:
877 result[elem] = count
878 return result
879
880 def __and__(self, other):
881 ''' Intersection is the minimum of corresponding counts.
882
883 >>> Counter('abbb') & Counter('bcc')
884 Counter({'b': 1})
885
886 '''
887 if not isinstance(other, Counter):
888 return NotImplemented
889 result = Counter()
890 for elem, count in self.items():
891 other_count = other[elem]
892 newcount = count if count < other_count else other_count
893 if newcount > 0:
894 result[elem] = newcount
895 return result
896
897 def __pos__(self):
898 'Adds an empty counter, effectively stripping negative and zero counts'
899 result = Counter()
900 for elem, count in self.items():
901 if count > 0:
902 result[elem] = count
903 return result
904
905 def __neg__(self):
906 '''Subtracts from an empty counter. Strips positive and zero counts,
907 and flips the sign on negative counts.
908
909 '''
910 result = Counter()
911 for elem, count in self.items():
912 if count < 0:
913 result[elem] = 0 - count
914 return result
915
916 def _keep_positive(self):
917 '''Internal method to strip elements with a negative or zero count'''
918 nonpositive = [elem for elem, count in self.items() if not count > 0]
919 for elem in nonpositive:
920 del self[elem]
921 return self
922
923 def __iadd__(self, other):
924 '''Inplace add from another counter, keeping only positive counts.
925
926 >>> c = Counter('abbb')
927 >>> c += Counter('bcc')
928 >>> c
929 Counter({'b': 4, 'c': 2, 'a': 1})
930
931 '''
932 for elem, count in other.items():
933 self[elem] += count
934 return self._keep_positive()
935
936 def __isub__(self, other):
937 '''Inplace subtract counter, but keep only results with positive counts.
938
939 >>> c = Counter('abbbc')
940 >>> c -= Counter('bccd')
941 >>> c
942 Counter({'b': 2, 'a': 1})
943
944 '''
945 for elem, count in other.items():
946 self[elem] -= count
947 return self._keep_positive()
948
949 def __ior__(self, other):
950 '''Inplace union is the maximum of value from either counter.
951
952 >>> c = Counter('abbb')
953 >>> c |= Counter('bcc')
954 >>> c
955 Counter({'b': 3, 'c': 2, 'a': 1})
956
957 '''
958 for elem, other_count in other.items():
959 count = self[elem]
960 if other_count > count:
961 self[elem] = other_count
962 return self._keep_positive()
963
964 def __iand__(self, other):
965 '''Inplace intersection is the minimum of corresponding counts.
966
967 >>> c = Counter('abbb')
968 >>> c &= Counter('bcc')
969 >>> c
970 Counter({'b': 1})
971
972 '''
973 for elem, count in self.items():
974 other_count = other[elem]
975 if other_count < count:
976 self[elem] = other_count
977 return self._keep_positive()
978
979
980 ########################################################################
981 ### ChainMap
982 ########################################################################
983
984 class ESC[4;38;5;81mChainMap(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mMutableMapping):
985 ''' A ChainMap groups multiple dicts (or other mappings) together
986 to create a single, updateable view.
987
988 The underlying mappings are stored in a list. That list is public and can
989 be accessed or updated using the *maps* attribute. There is no other
990 state.
991
992 Lookups search the underlying mappings successively until a key is found.
993 In contrast, writes, updates, and deletions only operate on the first
994 mapping.
995
996 '''
997
998 def __init__(self, *maps):
999 '''Initialize a ChainMap by setting *maps* to the given mappings.
1000 If no mappings are provided, a single empty dictionary is used.
1001
1002 '''
1003 self.maps = list(maps) or [{}] # always at least one map
1004
1005 def __missing__(self, key):
1006 raise KeyError(key)
1007
1008 def __getitem__(self, key):
1009 for mapping in self.maps:
1010 try:
1011 return mapping[key] # can't use 'key in mapping' with defaultdict
1012 except KeyError:
1013 pass
1014 return self.__missing__(key) # support subclasses that define __missing__
1015
1016 def get(self, key, default=None):
1017 return self[key] if key in self else default
1018
1019 def __len__(self):
1020 return len(set().union(*self.maps)) # reuses stored hash values if possible
1021
1022 def __iter__(self):
1023 d = {}
1024 for mapping in map(dict.fromkeys, reversed(self.maps)):
1025 d |= mapping # reuses stored hash values if possible
1026 return iter(d)
1027
1028 def __contains__(self, key):
1029 return any(key in m for m in self.maps)
1030
1031 def __bool__(self):
1032 return any(self.maps)
1033
1034 @_recursive_repr()
1035 def __repr__(self):
1036 return f'{self.__class__.__name__}({", ".join(map(repr, self.maps))})'
1037
1038 @classmethod
1039 def fromkeys(cls, iterable, *args):
1040 'Create a ChainMap with a single dict created from the iterable.'
1041 return cls(dict.fromkeys(iterable, *args))
1042
1043 def copy(self):
1044 'New ChainMap or subclass with a new copy of maps[0] and refs to maps[1:]'
1045 return self.__class__(self.maps[0].copy(), *self.maps[1:])
1046
1047 __copy__ = copy
1048
1049 def new_child(self, m=None, **kwargs): # like Django's Context.push()
1050 '''New ChainMap with a new map followed by all previous maps.
1051 If no map is provided, an empty dict is used.
1052 Keyword arguments update the map or new empty dict.
1053 '''
1054 if m is None:
1055 m = kwargs
1056 elif kwargs:
1057 m.update(kwargs)
1058 return self.__class__(m, *self.maps)
1059
1060 @property
1061 def parents(self): # like Django's Context.pop()
1062 'New ChainMap from maps[1:].'
1063 return self.__class__(*self.maps[1:])
1064
1065 def __setitem__(self, key, value):
1066 self.maps[0][key] = value
1067
1068 def __delitem__(self, key):
1069 try:
1070 del self.maps[0][key]
1071 except KeyError:
1072 raise KeyError(f'Key not found in the first mapping: {key!r}')
1073
1074 def popitem(self):
1075 'Remove and return an item pair from maps[0]. Raise KeyError is maps[0] is empty.'
1076 try:
1077 return self.maps[0].popitem()
1078 except KeyError:
1079 raise KeyError('No keys found in the first mapping.')
1080
1081 def pop(self, key, *args):
1082 'Remove *key* from maps[0] and return its value. Raise KeyError if *key* not in maps[0].'
1083 try:
1084 return self.maps[0].pop(key, *args)
1085 except KeyError:
1086 raise KeyError(f'Key not found in the first mapping: {key!r}')
1087
1088 def clear(self):
1089 'Clear maps[0], leaving maps[1:] intact.'
1090 self.maps[0].clear()
1091
1092 def __ior__(self, other):
1093 self.maps[0].update(other)
1094 return self
1095
1096 def __or__(self, other):
1097 if not isinstance(other, _collections_abc.Mapping):
1098 return NotImplemented
1099 m = self.copy()
1100 m.maps[0].update(other)
1101 return m
1102
1103 def __ror__(self, other):
1104 if not isinstance(other, _collections_abc.Mapping):
1105 return NotImplemented
1106 m = dict(other)
1107 for child in reversed(self.maps):
1108 m.update(child)
1109 return self.__class__(m)
1110
1111
1112 ################################################################################
1113 ### UserDict
1114 ################################################################################
1115
1116 class ESC[4;38;5;81mUserDict(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mMutableMapping):
1117
1118 # Start by filling-out the abstract methods
1119 def __init__(self, dict=None, /, **kwargs):
1120 self.data = {}
1121 if dict is not None:
1122 self.update(dict)
1123 if kwargs:
1124 self.update(kwargs)
1125
1126 def __len__(self):
1127 return len(self.data)
1128
1129 def __getitem__(self, key):
1130 if key in self.data:
1131 return self.data[key]
1132 if hasattr(self.__class__, "__missing__"):
1133 return self.__class__.__missing__(self, key)
1134 raise KeyError(key)
1135
1136 def __setitem__(self, key, item):
1137 self.data[key] = item
1138
1139 def __delitem__(self, key):
1140 del self.data[key]
1141
1142 def __iter__(self):
1143 return iter(self.data)
1144
1145 # Modify __contains__ and get() to work like dict
1146 # does when __missing__ is present.
1147 def __contains__(self, key):
1148 return key in self.data
1149
1150 def get(self, key, default=None):
1151 if key in self:
1152 return self[key]
1153 return default
1154
1155
1156 # Now, add the methods in dicts but not in MutableMapping
1157 def __repr__(self):
1158 return repr(self.data)
1159
1160 def __or__(self, other):
1161 if isinstance(other, UserDict):
1162 return self.__class__(self.data | other.data)
1163 if isinstance(other, dict):
1164 return self.__class__(self.data | other)
1165 return NotImplemented
1166
1167 def __ror__(self, other):
1168 if isinstance(other, UserDict):
1169 return self.__class__(other.data | self.data)
1170 if isinstance(other, dict):
1171 return self.__class__(other | self.data)
1172 return NotImplemented
1173
1174 def __ior__(self, other):
1175 if isinstance(other, UserDict):
1176 self.data |= other.data
1177 else:
1178 self.data |= other
1179 return self
1180
1181 def __copy__(self):
1182 inst = self.__class__.__new__(self.__class__)
1183 inst.__dict__.update(self.__dict__)
1184 # Create a copy and avoid triggering descriptors
1185 inst.__dict__["data"] = self.__dict__["data"].copy()
1186 return inst
1187
1188 def copy(self):
1189 if self.__class__ is UserDict:
1190 return UserDict(self.data.copy())
1191 import copy
1192 data = self.data
1193 try:
1194 self.data = {}
1195 c = copy.copy(self)
1196 finally:
1197 self.data = data
1198 c.update(self)
1199 return c
1200
1201 @classmethod
1202 def fromkeys(cls, iterable, value=None):
1203 d = cls()
1204 for key in iterable:
1205 d[key] = value
1206 return d
1207
1208
1209 ################################################################################
1210 ### UserList
1211 ################################################################################
1212
1213 class ESC[4;38;5;81mUserList(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mMutableSequence):
1214 """A more or less complete user-defined wrapper around list objects."""
1215
1216 def __init__(self, initlist=None):
1217 self.data = []
1218 if initlist is not None:
1219 # XXX should this accept an arbitrary sequence?
1220 if type(initlist) == type(self.data):
1221 self.data[:] = initlist
1222 elif isinstance(initlist, UserList):
1223 self.data[:] = initlist.data[:]
1224 else:
1225 self.data = list(initlist)
1226
1227 def __repr__(self):
1228 return repr(self.data)
1229
1230 def __lt__(self, other):
1231 return self.data < self.__cast(other)
1232
1233 def __le__(self, other):
1234 return self.data <= self.__cast(other)
1235
1236 def __eq__(self, other):
1237 return self.data == self.__cast(other)
1238
1239 def __gt__(self, other):
1240 return self.data > self.__cast(other)
1241
1242 def __ge__(self, other):
1243 return self.data >= self.__cast(other)
1244
1245 def __cast(self, other):
1246 return other.data if isinstance(other, UserList) else other
1247
1248 def __contains__(self, item):
1249 return item in self.data
1250
1251 def __len__(self):
1252 return len(self.data)
1253
1254 def __getitem__(self, i):
1255 if isinstance(i, slice):
1256 return self.__class__(self.data[i])
1257 else:
1258 return self.data[i]
1259
1260 def __setitem__(self, i, item):
1261 self.data[i] = item
1262
1263 def __delitem__(self, i):
1264 del self.data[i]
1265
1266 def __add__(self, other):
1267 if isinstance(other, UserList):
1268 return self.__class__(self.data + other.data)
1269 elif isinstance(other, type(self.data)):
1270 return self.__class__(self.data + other)
1271 return self.__class__(self.data + list(other))
1272
1273 def __radd__(self, other):
1274 if isinstance(other, UserList):
1275 return self.__class__(other.data + self.data)
1276 elif isinstance(other, type(self.data)):
1277 return self.__class__(other + self.data)
1278 return self.__class__(list(other) + self.data)
1279
1280 def __iadd__(self, other):
1281 if isinstance(other, UserList):
1282 self.data += other.data
1283 elif isinstance(other, type(self.data)):
1284 self.data += other
1285 else:
1286 self.data += list(other)
1287 return self
1288
1289 def __mul__(self, n):
1290 return self.__class__(self.data * n)
1291
1292 __rmul__ = __mul__
1293
1294 def __imul__(self, n):
1295 self.data *= n
1296 return self
1297
1298 def __copy__(self):
1299 inst = self.__class__.__new__(self.__class__)
1300 inst.__dict__.update(self.__dict__)
1301 # Create a copy and avoid triggering descriptors
1302 inst.__dict__["data"] = self.__dict__["data"][:]
1303 return inst
1304
1305 def append(self, item):
1306 self.data.append(item)
1307
1308 def insert(self, i, item):
1309 self.data.insert(i, item)
1310
1311 def pop(self, i=-1):
1312 return self.data.pop(i)
1313
1314 def remove(self, item):
1315 self.data.remove(item)
1316
1317 def clear(self):
1318 self.data.clear()
1319
1320 def copy(self):
1321 return self.__class__(self)
1322
1323 def count(self, item):
1324 return self.data.count(item)
1325
1326 def index(self, item, *args):
1327 return self.data.index(item, *args)
1328
1329 def reverse(self):
1330 self.data.reverse()
1331
1332 def sort(self, /, *args, **kwds):
1333 self.data.sort(*args, **kwds)
1334
1335 def extend(self, other):
1336 if isinstance(other, UserList):
1337 self.data.extend(other.data)
1338 else:
1339 self.data.extend(other)
1340
1341
1342 ################################################################################
1343 ### UserString
1344 ################################################################################
1345
1346 class ESC[4;38;5;81mUserString(ESC[4;38;5;149m_collections_abcESC[4;38;5;149m.ESC[4;38;5;149mSequence):
1347
1348 def __init__(self, seq):
1349 if isinstance(seq, str):
1350 self.data = seq
1351 elif isinstance(seq, UserString):
1352 self.data = seq.data[:]
1353 else:
1354 self.data = str(seq)
1355
1356 def __str__(self):
1357 return str(self.data)
1358
1359 def __repr__(self):
1360 return repr(self.data)
1361
1362 def __int__(self):
1363 return int(self.data)
1364
1365 def __float__(self):
1366 return float(self.data)
1367
1368 def __complex__(self):
1369 return complex(self.data)
1370
1371 def __hash__(self):
1372 return hash(self.data)
1373
1374 def __getnewargs__(self):
1375 return (self.data[:],)
1376
1377 def __eq__(self, string):
1378 if isinstance(string, UserString):
1379 return self.data == string.data
1380 return self.data == string
1381
1382 def __lt__(self, string):
1383 if isinstance(string, UserString):
1384 return self.data < string.data
1385 return self.data < string
1386
1387 def __le__(self, string):
1388 if isinstance(string, UserString):
1389 return self.data <= string.data
1390 return self.data <= string
1391
1392 def __gt__(self, string):
1393 if isinstance(string, UserString):
1394 return self.data > string.data
1395 return self.data > string
1396
1397 def __ge__(self, string):
1398 if isinstance(string, UserString):
1399 return self.data >= string.data
1400 return self.data >= string
1401
1402 def __contains__(self, char):
1403 if isinstance(char, UserString):
1404 char = char.data
1405 return char in self.data
1406
1407 def __len__(self):
1408 return len(self.data)
1409
1410 def __getitem__(self, index):
1411 return self.__class__(self.data[index])
1412
1413 def __add__(self, other):
1414 if isinstance(other, UserString):
1415 return self.__class__(self.data + other.data)
1416 elif isinstance(other, str):
1417 return self.__class__(self.data + other)
1418 return self.__class__(self.data + str(other))
1419
1420 def __radd__(self, other):
1421 if isinstance(other, str):
1422 return self.__class__(other + self.data)
1423 return self.__class__(str(other) + self.data)
1424
1425 def __mul__(self, n):
1426 return self.__class__(self.data * n)
1427
1428 __rmul__ = __mul__
1429
1430 def __mod__(self, args):
1431 return self.__class__(self.data % args)
1432
1433 def __rmod__(self, template):
1434 return self.__class__(str(template) % self)
1435
1436 # the following methods are defined in alphabetical order:
1437 def capitalize(self):
1438 return self.__class__(self.data.capitalize())
1439
1440 def casefold(self):
1441 return self.__class__(self.data.casefold())
1442
1443 def center(self, width, *args):
1444 return self.__class__(self.data.center(width, *args))
1445
1446 def count(self, sub, start=0, end=_sys.maxsize):
1447 if isinstance(sub, UserString):
1448 sub = sub.data
1449 return self.data.count(sub, start, end)
1450
1451 def removeprefix(self, prefix, /):
1452 if isinstance(prefix, UserString):
1453 prefix = prefix.data
1454 return self.__class__(self.data.removeprefix(prefix))
1455
1456 def removesuffix(self, suffix, /):
1457 if isinstance(suffix, UserString):
1458 suffix = suffix.data
1459 return self.__class__(self.data.removesuffix(suffix))
1460
1461 def encode(self, encoding='utf-8', errors='strict'):
1462 encoding = 'utf-8' if encoding is None else encoding
1463 errors = 'strict' if errors is None else errors
1464 return self.data.encode(encoding, errors)
1465
1466 def endswith(self, suffix, start=0, end=_sys.maxsize):
1467 return self.data.endswith(suffix, start, end)
1468
1469 def expandtabs(self, tabsize=8):
1470 return self.__class__(self.data.expandtabs(tabsize))
1471
1472 def find(self, sub, start=0, end=_sys.maxsize):
1473 if isinstance(sub, UserString):
1474 sub = sub.data
1475 return self.data.find(sub, start, end)
1476
1477 def format(self, /, *args, **kwds):
1478 return self.data.format(*args, **kwds)
1479
1480 def format_map(self, mapping):
1481 return self.data.format_map(mapping)
1482
1483 def index(self, sub, start=0, end=_sys.maxsize):
1484 return self.data.index(sub, start, end)
1485
1486 def isalpha(self):
1487 return self.data.isalpha()
1488
1489 def isalnum(self):
1490 return self.data.isalnum()
1491
1492 def isascii(self):
1493 return self.data.isascii()
1494
1495 def isdecimal(self):
1496 return self.data.isdecimal()
1497
1498 def isdigit(self):
1499 return self.data.isdigit()
1500
1501 def isidentifier(self):
1502 return self.data.isidentifier()
1503
1504 def islower(self):
1505 return self.data.islower()
1506
1507 def isnumeric(self):
1508 return self.data.isnumeric()
1509
1510 def isprintable(self):
1511 return self.data.isprintable()
1512
1513 def isspace(self):
1514 return self.data.isspace()
1515
1516 def istitle(self):
1517 return self.data.istitle()
1518
1519 def isupper(self):
1520 return self.data.isupper()
1521
1522 def join(self, seq):
1523 return self.data.join(seq)
1524
1525 def ljust(self, width, *args):
1526 return self.__class__(self.data.ljust(width, *args))
1527
1528 def lower(self):
1529 return self.__class__(self.data.lower())
1530
1531 def lstrip(self, chars=None):
1532 return self.__class__(self.data.lstrip(chars))
1533
1534 maketrans = str.maketrans
1535
1536 def partition(self, sep):
1537 return self.data.partition(sep)
1538
1539 def replace(self, old, new, maxsplit=-1):
1540 if isinstance(old, UserString):
1541 old = old.data
1542 if isinstance(new, UserString):
1543 new = new.data
1544 return self.__class__(self.data.replace(old, new, maxsplit))
1545
1546 def rfind(self, sub, start=0, end=_sys.maxsize):
1547 if isinstance(sub, UserString):
1548 sub = sub.data
1549 return self.data.rfind(sub, start, end)
1550
1551 def rindex(self, sub, start=0, end=_sys.maxsize):
1552 return self.data.rindex(sub, start, end)
1553
1554 def rjust(self, width, *args):
1555 return self.__class__(self.data.rjust(width, *args))
1556
1557 def rpartition(self, sep):
1558 return self.data.rpartition(sep)
1559
1560 def rstrip(self, chars=None):
1561 return self.__class__(self.data.rstrip(chars))
1562
1563 def split(self, sep=None, maxsplit=-1):
1564 return self.data.split(sep, maxsplit)
1565
1566 def rsplit(self, sep=None, maxsplit=-1):
1567 return self.data.rsplit(sep, maxsplit)
1568
1569 def splitlines(self, keepends=False):
1570 return self.data.splitlines(keepends)
1571
1572 def startswith(self, prefix, start=0, end=_sys.maxsize):
1573 return self.data.startswith(prefix, start, end)
1574
1575 def strip(self, chars=None):
1576 return self.__class__(self.data.strip(chars))
1577
1578 def swapcase(self):
1579 return self.__class__(self.data.swapcase())
1580
1581 def title(self):
1582 return self.__class__(self.data.title())
1583
1584 def translate(self, *args):
1585 return self.__class__(self.data.translate(*args))
1586
1587 def upper(self):
1588 return self.__class__(self.data.upper())
1589
1590 def zfill(self, width):
1591 return self.__class__(self.data.zfill(width))