1. Pypy
  2. Untitled project
  3. pypy

Commits

Manuel Jacob  committed 53becf1

Implement str.format_map().

  • Participants
  • Parent commits 442dad6
  • Branches py3k

Comments (0)

Files changed (4)

File pypy/objspace/std/newformat.py

View file
             self.empty = u"" if is_unicode else ""
             self.template = template
 
-        def build(self, args):
-            self.args, self.kwargs = args.unpack()
+        def build(self, args, w_kwargs):
+            self.args = args
+            self.w_kwargs = w_kwargs
             self.auto_numbering = 0
             self.auto_numbering_state = ANS_INIT
             return self._build_string(0, len(self.template), 2)
                         raise OperationError(space.w_KeyError, space.wrap(kwarg))
                 else:
                     arg_key = kwarg
-                try:
-                    w_arg = self.kwargs[arg_key]
-                except KeyError:
-                    raise OperationError(space.w_KeyError, space.wrap(arg_key))
+                w_arg = space.getitem(self.w_kwargs, space.wrap(arg_key))
             else:
+                if self.args is None:
+                    w_msg = space.wrap("Format string contains positional "
+                                       "fields")
+                    raise OperationError(space.w_ValueError, w_msg)
                 try:
                     w_arg = self.args[index]
                 except IndexError:
     return UnicodeTemplateFormatter(space, True, template)
 
 
-def format_method(space, w_string, args, is_unicode):
+def format_method(space, w_string, args, w_kwargs, is_unicode):
     if is_unicode:
         template = unicode_template_formatter(space,
                                               space.unicode_w(w_string))
-        return space.wrap(template.build(args))
+        return space.wrap(template.build(args, w_kwargs))
     else:
         template = str_template_formatter(space, space.bytes_w(w_string))
-        return space.wrap(template.build(args))
+        return space.wrap(template.build(args, w_kwargs))
 
 
 class NumberSpec(object):

File pypy/objspace/std/test/test_unicodeobject.py

View file
         assert b == 'hello \u1234'
 
         assert '%s' % S('mar\xe7') == 'mar\xe7'
+
+    def test_format_new(self):
+        assert '0{0}1{b}2'.format('A', b='B') == '0A1B2'
+
+    def test_format_map(self):
+        assert '0{a}1'.format_map({'a': 'A'}) == '0A1'
+
+    def test_format_map_positional(self):
+        raises(ValueError, '{}'.format_map, {})

File pypy/objspace/std/unicodeobject.py

View file
     return mod_format(space, w_format, w_values, do_unicode=True)
 
 def unicode_format__Unicode(space, w_unicode, __args__):
-    return newformat.format_method(space, w_unicode, __args__, True)
+    w_kwds = space.newdict()
+    if __args__.keywords:
+        for i in range(len(__args__.keywords)):
+            space.setitem(w_kwds, space.wrap(__args__.keywords[i]),
+                          __args__.keywords_w[i])
+    return newformat.format_method(space, w_unicode, __args__.arguments_w,
+                                   w_kwds, True)
+
+def unicode_format_map__Unicode_ANY(space, w_unicode, w_mapping):
+    return newformat.format_method(space, w_unicode, None, w_mapping, True)
 
 def format__Unicode_ANY(space, w_unicode, w_spec):
     return newformat.run_formatter(space, w_spec, "format_string", w_unicode)

File pypy/objspace/std/unicodetype.py

View file
                              ' size of 8 characters is assumed.')
 unicode_format     = SMM('format', 1, general__args__=True,
                          doc='S.format() -> new style formating')
+unicode_format_map = SMM('format_map', 2,
+                         doc='S.format_map(mapping) -> str')
 unicode_isalnum    = SMM('isalnum', 1,
                          doc='S.isalnum() -> bool\n\nReturn True if all'
                              ' characters in S are alphanumeric\nand there is'