Commit 573b44c1 authored by Raymond Hettinger's avatar Raymond Hettinger

Issue 22189: Add missing methods to UserString

parent ab89f9c2
...@@ -1060,6 +1060,8 @@ class UserString(Sequence): ...@@ -1060,6 +1060,8 @@ class UserString(Sequence):
def __float__(self): return float(self.data) def __float__(self): return float(self.data)
def __complex__(self): return complex(self.data) def __complex__(self): return complex(self.data)
def __hash__(self): return hash(self.data) def __hash__(self): return hash(self.data)
def __getnewargs__(self):
return (self.data[:],)
def __eq__(self, string): def __eq__(self, string):
if isinstance(string, UserString): if isinstance(string, UserString):
...@@ -1104,9 +1106,13 @@ class UserString(Sequence): ...@@ -1104,9 +1106,13 @@ class UserString(Sequence):
__rmul__ = __mul__ __rmul__ = __mul__
def __mod__(self, args): def __mod__(self, args):
return self.__class__(self.data % args) return self.__class__(self.data % args)
def __rmod__(self, format):
return self.__class__(format % args)
# the following methods are defined in alphabetical order: # the following methods are defined in alphabetical order:
def capitalize(self): return self.__class__(self.data.capitalize()) def capitalize(self): return self.__class__(self.data.capitalize())
def casefold(self):
return self.__class__(self.data.casefold())
def center(self, width, *args): def center(self, width, *args):
return self.__class__(self.data.center(width, *args)) return self.__class__(self.data.center(width, *args))
def count(self, sub, start=0, end=_sys.maxsize): def count(self, sub, start=0, end=_sys.maxsize):
...@@ -1129,6 +1135,8 @@ class UserString(Sequence): ...@@ -1129,6 +1135,8 @@ class UserString(Sequence):
return self.data.find(sub, start, end) return self.data.find(sub, start, end)
def format(self, *args, **kwds): def format(self, *args, **kwds):
return self.data.format(*args, **kwds) return self.data.format(*args, **kwds)
def format_map(self, mapping):
return self.data.format_map(mapping)
def index(self, sub, start=0, end=_sys.maxsize): def index(self, sub, start=0, end=_sys.maxsize):
return self.data.index(sub, start, end) return self.data.index(sub, start, end)
def isalpha(self): return self.data.isalpha() def isalpha(self): return self.data.isalpha()
...@@ -1138,6 +1146,7 @@ class UserString(Sequence): ...@@ -1138,6 +1146,7 @@ class UserString(Sequence):
def isidentifier(self): return self.data.isidentifier() def isidentifier(self): return self.data.isidentifier()
def islower(self): return self.data.islower() def islower(self): return self.data.islower()
def isnumeric(self): return self.data.isnumeric() def isnumeric(self): return self.data.isnumeric()
def isprintable(self): return self.data.isprintable()
def isspace(self): return self.data.isspace() def isspace(self): return self.data.isspace()
def istitle(self): return self.data.istitle() def istitle(self): return self.data.istitle()
def isupper(self): return self.data.isupper() def isupper(self): return self.data.isupper()
...@@ -1146,6 +1155,7 @@ class UserString(Sequence): ...@@ -1146,6 +1155,7 @@ class UserString(Sequence):
return self.__class__(self.data.ljust(width, *args)) return self.__class__(self.data.ljust(width, *args))
def lower(self): return self.__class__(self.data.lower()) def lower(self): return self.__class__(self.data.lower())
def lstrip(self, chars=None): return self.__class__(self.data.lstrip(chars)) def lstrip(self, chars=None): return self.__class__(self.data.lstrip(chars))
maketrans = str.maketrans
def partition(self, sep): def partition(self, sep):
return self.data.partition(sep) return self.data.partition(sep)
def replace(self, old, new, maxsplit=-1): def replace(self, old, new, maxsplit=-1):
......
...@@ -12,7 +12,7 @@ import keyword ...@@ -12,7 +12,7 @@ import keyword
import re import re
import sys import sys
import types import types
from collections import UserDict from collections import UserDict, UserString, UserList
from collections import ChainMap from collections import ChainMap
from collections import deque from collections import deque
from collections.abc import Awaitable, Coroutine, AsyncIterator, AsyncIterable from collections.abc import Awaitable, Coroutine, AsyncIterator, AsyncIterable
...@@ -24,6 +24,26 @@ from collections.abc import Sequence, MutableSequence ...@@ -24,6 +24,26 @@ from collections.abc import Sequence, MutableSequence
from collections.abc import ByteString from collections.abc import ByteString
class TestUserObjects(unittest.TestCase):
def _superset_test(self, a, b):
self.assertGreaterEqual(
set(dir(a)),
set(dir(b)),
'{a} should have all the methods of {b}'.format(
a=a.__name__,
b=b.__name__,
),
)
def test_str_protocol(self):
self._superset_test(UserString, str)
def test_list_protocol(self):
self._superset_test(UserList, list)
def test_dict_protocol(self):
self._superset_test(UserDict, dict)
################################################################################ ################################################################################
### ChainMap (helper class for configparser and the string module) ### ChainMap (helper class for configparser and the string module)
################################################################################ ################################################################################
...@@ -1848,7 +1868,8 @@ def test_main(verbose=None): ...@@ -1848,7 +1868,8 @@ def test_main(verbose=None):
NamedTupleDocs = doctest.DocTestSuite(module=collections) NamedTupleDocs = doctest.DocTestSuite(module=collections)
test_classes = [TestNamedTuple, NamedTupleDocs, TestOneTrickPonyABCs, test_classes = [TestNamedTuple, NamedTupleDocs, TestOneTrickPonyABCs,
TestCollectionABCs, TestCounter, TestChainMap, TestCollectionABCs, TestCounter, TestChainMap,
TestOrderedDict, GeneralMappingTests, SubclassMappingTests] TestOrderedDict, GeneralMappingTests, SubclassMappingTests,
TestUserObjects]
support.run_unittest(*test_classes) support.run_unittest(*test_classes)
support.run_doctest(collections, verbose) support.run_doctest(collections, verbose)
......
...@@ -64,6 +64,10 @@ Library ...@@ -64,6 +64,10 @@ Library
- Issue 24230: The tempfile module now accepts bytes for prefix, suffix and dir - Issue 24230: The tempfile module now accepts bytes for prefix, suffix and dir
parameters and returns bytes in such situations (matching the os module APIs). parameters and returns bytes in such situations (matching the os module APIs).
- Issue #22189: collections.UserString now supports __getnewargs__(),
__rmod__(), casefold(), format_map(), isprintable(), and maketrans().
Patch by Joe Jevnik.
- Issue 24244: Prevents termination when an invalid format string is - Issue 24244: Prevents termination when an invalid format string is
encountered on Windows in strftime. encountered on Windows in strftime.
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment