[pypy-svn] r42011 - in pypy/dist/pypy/objspace/std: . test

fijal at codespeak.net fijal at codespeak.net
Thu Apr 12 22:00:58 CEST 2007


Author: fijal
Date: Thu Apr 12 22:00:57 2007
New Revision: 42011

Added:
   pypy/dist/pypy/objspace/std/formatting.py
      - copied, changed from r41900, pypy/dist/pypy/lib/_formatting.py
Modified:
   pypy/dist/pypy/objspace/std/ropeobject.py
   pypy/dist/pypy/objspace/std/stringobject.py
   pypy/dist/pypy/objspace/std/test/test_stringformat.py
   pypy/dist/pypy/objspace/std/unicodeobject.py
Log:
Make string formatting RPython.
* It's faster
* It rather works (tests passes at least, also CPython regr tests)
* The unicode support is a hack, let's wait for proper RPython
  unicode support to do it better
* Long overflow is a bit slow (space op everywhere)
* Few spaceops can be removed
* There is still pending alloc removal, because ValueBox is not longer
  needed at all.


Modified: pypy/dist/pypy/objspace/std/ropeobject.py
==============================================================================
--- pypy/dist/pypy/objspace/std/ropeobject.py	(original)
+++ pypy/dist/pypy/objspace/std/ropeobject.py	Thu Apr 12 22:00:57 2007
@@ -11,6 +11,7 @@
 from pypy.objspace.std.stringtype import wrapchar
 
 from pypy.objspace.std import rope
+from pypy.objspace.std.stringobject import mod__String_ANY as mod__Rope_ANY
 
 class W_RopeObject(W_Object):
     from pypy.objspace.std.stringtype import str_typedef as typedef
@@ -1061,28 +1062,9 @@
             return codecs.getencoder(encoding)(str, errors)[0]
 ''', filename=__file__) 
 
-# this one should do the import of _formatting:
-app2 = gateway.applevel('''
-    import _formatting
-
-    def mod__Rope_ANY(format, values):
-        if isinstance(values, tuple):
-            return _formatting.format(format, values, None)
-        else:
-            # CPython's logic for deciding if  ""%values  is
-            # an error (1 value, 0 %-formatters) or not
-            # (values is of a mapping type)
-            if (hasattr(values, '__getitem__')
-                and not isinstance(values, basestring)):
-                return _formatting.format(format, (values,), values)
-            else:
-                return _formatting.format(format, (values,), None)
-''', filename=__file__)
-
 str_translate__Rope_ANY_ANY = app.interphook('str_translate__Rope_ANY_ANY') 
 str_decode__Rope_ANY_ANY = app.interphook('str_decode__Rope_ANY_ANY') 
 str_encode__Rope_ANY_ANY = app.interphook('str_encode__Rope_ANY_ANY') 
-mod__Rope_ANY = app2.interphook('mod__Rope_ANY') 
 
 # methods of the iterator
 

Modified: pypy/dist/pypy/objspace/std/stringobject.py
==============================================================================
--- pypy/dist/pypy/objspace/std/stringobject.py	(original)
+++ pypy/dist/pypy/objspace/std/stringobject.py	Thu Apr 12 22:00:57 2007
@@ -14,6 +14,7 @@
 from pypy.objspace.std.stringtype import sliced, joined, wrapstr, wrapchar, \
      stringendswith, stringstartswith
 
+from pypy.objspace.std.formatting import format
 
 class W_StringObject(W_Object):
     from pypy.objspace.std.stringtype import str_typedef as typedef
@@ -907,28 +908,28 @@
             return codecs.getencoder(encoding)(str, errors)[0]
 ''', filename=__file__) 
 
-# this one should do the import of _formatting:
-app2 = gateway.applevel('''
-    import _formatting
-
-    def mod__String_ANY(format, values):
-        if isinstance(values, tuple):
-            return _formatting.format(format, values, None)
-        else:
-            # CPython's logic for deciding if  ""%values  is
-            # an error (1 value, 0 %-formatters) or not
-            # (values is of a mapping type)
-            if (hasattr(values, '__getitem__')
-                and not isinstance(values, basestring)):
-                return _formatting.format(format, (values,), values)
-            else:
-                return _formatting.format(format, (values,), None)
-''', filename=__file__)
 
 str_translate__String_ANY_ANY = app.interphook('str_translate__String_ANY_ANY') 
 str_decode__String_ANY_ANY = app.interphook('str_decode__String_ANY_ANY') 
 str_encode__String_ANY_ANY = app.interphook('str_encode__String_ANY_ANY') 
-mod__String_ANY = app2.interphook('mod__String_ANY') 
+
+# CPython's logic for deciding if  ""%values  is
+# an error (1 value, 0 %-formatters) or not
+# (values is of a mapping type)
+def mod__String_ANY(space, w_format, w_values):
+    if space.is_true(space.isinstance(w_values, space.w_tuple)):
+        return format(space, w_format, w_values)
+    else:
+        # we check directly for dict to avoid obscure checking
+        # in simplest case
+        if space.is_true(space.isinstance(w_values, space.w_dict)) or \
+           (space.lookup(w_values, '__getitem__') and
+           not space.is_true(space.isinstance(w_values, space.w_basestring))):
+            return format(space, w_format,
+                                     space.newtuple([w_values]), w_values)
+        else:
+            return format(space, w_format,
+                                     space.newtuple([w_values]), None)
 
 # register all methods
 from pypy.objspace.std import stringtype

Modified: pypy/dist/pypy/objspace/std/test/test_stringformat.py
==============================================================================
--- pypy/dist/pypy/objspace/std/test/test_stringformat.py	(original)
+++ pypy/dist/pypy/objspace/std/test/test_stringformat.py	Thu Apr 12 22:00:57 2007
@@ -161,3 +161,24 @@
             return fmt % x
         raises(OverflowError, f, "%.70f", 2.0)
         raises(OverflowError, f, "%.110g", 2.0)
+
+class AppTestUnicodeObject:
+    def test_unicode_convert(self):
+        assert isinstance("%s" % (u"x"), unicode)
+
+    def test_unicode_d(self):
+        assert u"%.1d" % 3 == '3'
+
+    def test_unicode_overflow(self):
+        import sys
+        raises(OverflowError, 'u"%.*d" % (sys.maxint, 1)')
+
+    def test_unicode_format_a(self):
+        assert u'%x' % 10L == 'a'
+
+    def test_long_no_overflow(self):
+        assert "%x" % 100000000000L == "174876e800"
+
+    def test_missing_cases(self):
+        print '%032d' % -123456789012345678901234567890L
+        assert '%032d' % -123456789012345678901234567890L == '-0123456789012345678901234567890'

Modified: pypy/dist/pypy/objspace/std/unicodeobject.py
==============================================================================
--- pypy/dist/pypy/objspace/std/unicodeobject.py	(original)
+++ pypy/dist/pypy/objspace/std/unicodeobject.py	Thu Apr 12 22:00:57 2007
@@ -8,6 +8,8 @@
 from pypy.rlib.rarithmetic import intmask, ovfcheck
 from pypy.module.unicodedata import unicodedb_3_2_0 as unicodedb
 
+from pypy.objspace.std.formatting import format
+
 class W_UnicodeObject(W_Object):
     from pypy.objspace.std.unicodetype import unicode_typedef as typedef
 
@@ -857,22 +859,6 @@
                 raise TypeError("character mapping must return integer, None or unicode")
     return ''.join(result)
 
-def mod__Unicode_ANY(format, values):
-    import _formatting
-    if isinstance(values, tuple):
-        return _formatting.format(format, values, None, do_unicode=True)
-    else:
-        # CPython\'s logic for deciding if  ""%values  is
-        # an error (1 value, 0 %-formatters) or not
-        # (values is of a mapping type)
-        if (hasattr(values, "__getitem__")
-            and not isinstance(values, basestring)):
-            return _formatting.format(format, (values,), values,
-                                      do_unicode=True)
-        else:
-            return _formatting.format(format, (values,), None,
-                                      do_unicode=True)
-
 def unicode_encode__Unicode_ANY_ANY(unistr, encoding=None, errors=None):
     import codecs, sys
     if encoding is None:
@@ -1047,6 +1033,25 @@
     return space.wrap(''.join(result[:i]))
         
 #repr__Unicode = app.interphook('repr__Unicode') # uncomment when repr code is moved to _codecs
+
+def mod__Unicode_ANY(space, w_format, w_values):
+    if space.is_true(space.isinstance(w_values, space.w_tuple)):
+        return format(space, w_format, w_values, do_unicode=True)
+    else:
+        # we check directly for dict to avoid obscure checking
+        # in simplest case
+        if space.is_true(space.isinstance(w_values, space.w_dict)) or \
+           (space.lookup(w_values, '__getitem__') and
+           not space.is_true(space.isinstance(w_values, space.w_basestring))):
+            return format(space, w_format,
+                          space.newtuple([w_values]), w_values,
+                          do_unicode=True)
+        else:
+            return format(space, w_format,
+                          space.newtuple([w_values]), None,
+                          do_unicode=True)
+
+
 import unicodetype
 register_all(vars(), unicodetype)
 



More information about the Pypy-commit mailing list