[pypy-commit] pypy default: (jterrace, alex): Expose unsigned integer types in numpy and fix a typo. Fixed up the handling of unsigned64s which are larger in value than a long.

alex_gaynor noreply at buildbot.pypy.org
Sun Dec 11 06:49:55 CET 2011


Author: Alex Gaynor <alex.gaynor at gmail.com>
Branch: 
Changeset: r50363:716c084b46a1
Date: 2011-12-11 00:49 -0500
http://bitbucket.org/pypy/pypy/changeset/716c084b46a1/

Log:	(jterrace, alex): Expose unsigned integer types in numpy and fix a
	typo. Fixed up the handling of unsigned64s which are larger in
	value than a long.

diff --git a/pypy/module/micronumpy/__init__.py b/pypy/module/micronumpy/__init__.py
--- a/pypy/module/micronumpy/__init__.py
+++ b/pypy/module/micronumpy/__init__.py
@@ -24,11 +24,16 @@
         'number': 'interp_boxes.W_NumberBox',
         'integer': 'interp_boxes.W_IntegerBox',
         'signedinteger': 'interp_boxes.W_SignedIntegerBox',
+        'unsignedinteger': 'interp_boxes.W_UnsignedIntegerBox',
         'bool_': 'interp_boxes.W_BoolBox',
         'int8': 'interp_boxes.W_Int8Box',
+        'uint8': 'interp_boxes.W_UInt8Box',
         'int16': 'interp_boxes.W_Int16Box',
+        'uint16': 'interp_boxes.W_UInt16Box',
         'int32': 'interp_boxes.W_Int32Box',
+        'uint32': 'interp_boxes.W_UInt32Box',
         'int64': 'interp_boxes.W_Int64Box',
+        'uint64': 'interp_boxes.W_UInt64Box',
         'int_': 'interp_boxes.W_LongBox',
         'inexact': 'interp_boxes.W_InexactBox',
         'floating': 'interp_boxes.W_FloatingBox',
diff --git a/pypy/module/micronumpy/compile.py b/pypy/module/micronumpy/compile.py
--- a/pypy/module/micronumpy/compile.py
+++ b/pypy/module/micronumpy/compile.py
@@ -38,6 +38,7 @@
     w_ValueError = None
     w_TypeError = None
     w_IndexError = None
+    w_OverflowError = None
     w_None = None
 
     w_bool = "bool"
@@ -149,6 +150,10 @@
         # XXX array probably
         assert False
 
+    def exception_match(self, w_exc_type, w_check_class):
+        # Good enough for now
+        raise NotImplementedError
+
 class FloatObject(W_Root):
     tp = FakeSpace.w_float
     def __init__(self, floatval):
diff --git a/pypy/module/micronumpy/interp_boxes.py b/pypy/module/micronumpy/interp_boxes.py
--- a/pypy/module/micronumpy/interp_boxes.py
+++ b/pypy/module/micronumpy/interp_boxes.py
@@ -107,38 +107,38 @@
 class W_SignedIntegerBox(W_IntegerBox):
     pass
 
-class W_UnsignedIntgerBox(W_IntegerBox):
+class W_UnsignedIntegerBox(W_IntegerBox):
     pass
 
 class W_Int8Box(W_SignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("int8")
 
-class W_UInt8Box(W_UnsignedIntgerBox, PrimitiveBox):
+class W_UInt8Box(W_UnsignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("uint8")
 
 class W_Int16Box(W_SignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("int16")
 
-class W_UInt16Box(W_UnsignedIntgerBox, PrimitiveBox):
+class W_UInt16Box(W_UnsignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("uint16")
 
 class W_Int32Box(W_SignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("int32")
 
-class W_UInt32Box(W_UnsignedIntgerBox, PrimitiveBox):
+class W_UInt32Box(W_UnsignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("uint32")
 
 class W_LongBox(W_SignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("long")
 
-class W_ULongBox(W_UnsignedIntgerBox, PrimitiveBox):
+class W_ULongBox(W_UnsignedIntegerBox, PrimitiveBox):
     pass
 
 class W_Int64Box(W_SignedIntegerBox, PrimitiveBox):
     descr__new__, get_dtype = new_dtype_getter("int64")
 
-class W_UInt64Box(W_UnsignedIntgerBox, PrimitiveBox):
-    pass
+class W_UInt64Box(W_UnsignedIntegerBox, PrimitiveBox):
+    descr__new__, get_dtype = new_dtype_getter("uint64")
 
 class W_InexactBox(W_NumberBox):
     _attrs_ = ()
@@ -203,13 +203,18 @@
     __module__ = "numpypy",
 )
 
+W_UnsignedIntegerBox.typedef = TypeDef("unsignedinteger", W_IntegerBox.typedef,
+    __module__ = "numpypy",
+)
+
 W_Int8Box.typedef = TypeDef("int8", W_SignedIntegerBox.typedef,
     __module__ = "numpypy",
     __new__ = interp2app(W_Int8Box.descr__new__.im_func),
 )
 
-W_UInt8Box.typedef = TypeDef("uint8", W_UnsignedIntgerBox.typedef,
+W_UInt8Box.typedef = TypeDef("uint8", W_UnsignedIntegerBox.typedef,
     __module__ = "numpypy",
+    __new__ = interp2app(W_UInt8Box.descr__new__.im_func),
 )
 
 W_Int16Box.typedef = TypeDef("int16", W_SignedIntegerBox.typedef,
@@ -217,8 +222,9 @@
     __new__ = interp2app(W_Int16Box.descr__new__.im_func),
 )
 
-W_UInt16Box.typedef = TypeDef("uint16", W_UnsignedIntgerBox.typedef,
+W_UInt16Box.typedef = TypeDef("uint16", W_UnsignedIntegerBox.typedef,
     __module__ = "numpypy",
+    __new__ = interp2app(W_UInt16Box.descr__new__.im_func),
 )
 
 W_Int32Box.typedef = TypeDef("int32", W_SignedIntegerBox.typedef,
@@ -226,8 +232,9 @@
     __new__ = interp2app(W_Int32Box.descr__new__.im_func),
 )
 
-W_UInt32Box.typedef = TypeDef("uint32", W_UnsignedIntgerBox.typedef,
+W_UInt32Box.typedef = TypeDef("uint32", W_UnsignedIntegerBox.typedef,
     __module__ = "numpypy",
+    __new__ = interp2app(W_UInt32Box.descr__new__.im_func),
 )
 
 if LONG_BIT == 32:
@@ -238,7 +245,7 @@
     __module__ = "numpypy",
 )
 
-W_ULongBox.typedef = TypeDef("u" + long_name, W_UnsignedIntgerBox.typedef,
+W_ULongBox.typedef = TypeDef("u" + long_name, W_UnsignedIntegerBox.typedef,
     __module__ = "numpypy",
 )
 
@@ -247,8 +254,9 @@
     __new__ = interp2app(W_Int64Box.descr__new__.im_func),
 )
 
-W_UInt64Box.typedef = TypeDef("uint64", W_UnsignedIntgerBox.typedef,
+W_UInt64Box.typedef = TypeDef("uint64", W_UnsignedIntegerBox.typedef,
     __module__ = "numpypy",
+    __new__ = interp2app(W_UInt64Box.descr__new__.im_func),
 )
 
 W_InexactBox.typedef = TypeDef("inexact", W_NumberBox.typedef,
diff --git a/pypy/module/micronumpy/test/test_dtypes.py b/pypy/module/micronumpy/test/test_dtypes.py
--- a/pypy/module/micronumpy/test/test_dtypes.py
+++ b/pypy/module/micronumpy/test/test_dtypes.py
@@ -174,6 +174,8 @@
         raises(TypeError, numpy.integer, 0)
         exc = raises(TypeError, numpy.signedinteger, 0)
         assert str(exc.value) == "cannot create 'signedinteger' instances"
+        exc = raises(TypeError, numpy.unsignedinteger, 0)
+        assert str(exc.value) == "cannot create 'unsignedinteger' instances"
 
         raises(TypeError, numpy.floating, 0)
         raises(TypeError, numpy.inexact, 0)
@@ -210,17 +212,54 @@
         assert type(int(x)) is int
         assert int(x) == -128
 
+    def test_uint8(self):
+        import numpypy as numpy
+
+        assert numpy.uint8.mro() == [numpy.uint8, numpy.unsignedinteger, numpy.integer, numpy.number, numpy.generic, object]
+
+        a = numpy.array([1, 2, 3], numpy.uint8)
+        assert type(a[1]) is numpy.uint8
+        assert numpy.dtype("uint8").type is numpy.uint8
+
+        x = numpy.uint8(128)
+        assert x == 128
+        assert x != -128
+        assert type(x) is numpy.uint8
+        assert repr(x) == "128"
+
+        assert type(int(x)) is int
+        assert int(x) == 128
+
+        assert numpy.uint8(255) == 255
+        assert numpy.uint8(256) == 0
+
     def test_int16(self):
         import numpypy as numpy
 
         x = numpy.int16(3)
         assert x == 3
+        assert numpy.int16(32767) == 32767
+        assert numpy.int16(32768) == -32768
+
+    def test_uint16(self):
+        import numpypy as numpy
+
+        assert numpy.uint16(65535) == 65535
+        assert numpy.uint16(65536) == 0
 
     def test_int32(self):
         import numpypy as numpy
 
         x = numpy.int32(23)
         assert x == 23
+        assert numpy.int32(2147483647) == 2147483647
+        assert numpy.int32(2147483648) == -2147483648
+
+    def test_uint32(self):
+        import numpypy as numpy
+
+        assert numpy.uint32(4294967295) == 4294967295
+        assert numpy.uint32(4294967296) == 0
 
     def test_int_(self):
         import numpypy as numpy
@@ -240,6 +279,25 @@
         assert numpy.dtype(numpy.int64).type is numpy.int64
         assert numpy.int64(3) == 3
 
+        assert numpy.int64(9223372036854775807) == 9223372036854775807
+        raises(OverflowError, numpy.int64, 9223372036854775808)
+
+    def test_uint64(self):
+        import sys
+        import numpypy as numpy
+
+        assert numpy.uint64.mro() == [numpy.uint64, numpy.unsignedinteger, numpy.integer, numpy.number, numpy.generic, object]
+
+        assert numpy.dtype(numpy.uint64).type is numpy.uint64
+        skip("see comment")
+        # These tests pass "by chance" on numpy, things that are larger than
+        # platform long (i.e. a python int), don't get put in a normal box,
+        # instead they become an object array containing a long, we don't have
+        # yet, so these can't pass.
+        assert numpy.uint64(9223372036854775808) == 9223372036854775808
+        assert numpy.uint64(18446744073709551615) == 18446744073709551615
+        raises(OverflowError, numpy.uint64(18446744073709551616))
+
     def test_float32(self):
         import numpypy as numpy
 
diff --git a/pypy/module/micronumpy/types.py b/pypy/module/micronumpy/types.py
--- a/pypy/module/micronumpy/types.py
+++ b/pypy/module/micronumpy/types.py
@@ -1,6 +1,7 @@
 import functools
 import math
 
+from pypy.interpreter.error import OperationError
 from pypy.module.micronumpy import interp_boxes
 from pypy.objspace.std.floatobject import float2string
 from pypy.rlib import rfloat, libffi, clibffi
@@ -274,6 +275,19 @@
     T = rffi.ULONGLONG
     BoxType = interp_boxes.W_UInt64Box
 
+    def _coerce(self, space, w_item):
+        try:
+            return Integer._coerce(self, space, w_item)
+        except OperationError, e:
+            if not e.match(space, space.w_OverflowError):
+                raise
+        bigint = space.bigint_w(w_item)
+        try:
+            value = bigint.toulonglong()
+        except OverflowError:
+            raise OperationError(space.w_OverflowError, space.w_None)
+        return self.box(value)
+
 class Float(Primitive):
     _mixin_ = True
 


More information about the pypy-commit mailing list