[pypy-commit] pypy can_cast: Add stub implementation for can_cast(<value>, dtype)
rlamy
noreply at buildbot.pypy.org
Sun Apr 26 04:03:31 CEST 2015
Author: Ronan Lamy <ronan.lamy at gmail.com>
Branch: can_cast
Changeset: r76937:6aaed87e0b78
Date: 2015-04-26 03:03 +0100
http://bitbucket.org/pypy/pypy/changeset/6aaed87e0b78/
Log: Add stub implementation for can_cast(<value>, dtype)
diff --git a/pypy/module/micronumpy/arrayops.py b/pypy/module/micronumpy/arrayops.py
--- a/pypy/module/micronumpy/arrayops.py
+++ b/pypy/module/micronumpy/arrayops.py
@@ -306,7 +306,18 @@
def can_cast(space, w_from, w_totype, casting='safe'):
try:
target = as_dtype(space, w_totype, allow_None=False)
- origin = as_dtype(space, w_from, allow_None=False) # XXX
+ except TypeError:
+ raise oefmt(space.w_TypeError,
+ "did not understand one of the types; 'None' not accepted")
+ if isinstance(w_from, W_NDimArray):
+ return space.wrap(can_cast_array(space, w_from, target, casting))
+ elif is_scalar_w(space, w_from):
+ w_scalar = as_scalar(space, w_from)
+ w_arr = W_NDimArray.from_scalar(space, w_scalar)
+ return space.wrap(can_cast_array(space, w_arr, target, casting))
+
+ try:
+ origin = as_dtype(space, w_from, allow_None=False)
except TypeError:
raise oefmt(space.w_TypeError,
"did not understand one of the types; 'None' not accepted")
@@ -334,6 +345,30 @@
else:
return origin.can_cast_to(target)
+def can_cast_array(space, w_from, target, casting):
+ origin = w_from.get_dtype()
+ if w_from.is_scalar():
+ return can_cast_scalar(
+ space, origin, w_from.get_scalar_value(), target, casting)
+ else:
+ return can_cast_type(space, origin, target, casting)
+
+def can_cast_scalar(space, from_type, value, target, casting):
+ if from_type == target or casting == 'unsafe':
+ return True
+ if not from_type.is_number() or casting in ('no', 'equiv'):
+ return can_cast_type(space, from_type, target, casting)
+ if not from_type.is_native():
+ value = value.descr_byteswap(space)
+ return can_cast_type(space, from_type, target, casting) # XXX: stub impl
+
+def is_scalar_w(space, w_arg):
+ return (isinstance(w_arg, W_GenericBox) or
+ space.isinstance_w(w_arg, space.w_int) or
+ space.isinstance_w(w_arg, space.w_float) or
+ space.isinstance_w(w_arg, space.w_complex) or
+ space.isinstance_w(w_arg, space.w_long) or
+ space.isinstance_w(w_arg, space.w_bool))
def as_dtype(space, w_arg, allow_None=True):
# roughly equivalent to CNumPy's PyArray_DescrConverter2
@@ -341,13 +376,12 @@
raise TypeError("Cannot create dtype from None here")
if isinstance(w_arg, W_NDimArray):
return w_arg.get_dtype()
- elif isinstance(w_arg, W_GenericBox) or (
- space.isinstance_w(w_arg, space.w_int) or
- space.isinstance_w(w_arg, space.w_float) or
- space.isinstance_w(w_arg, space.w_complex) or
- space.isinstance_w(w_arg, space.w_long) or
- space.isinstance_w(w_arg, space.w_bool)):
+ elif is_scalar_w(space, w_arg):
return ufuncs.find_dtype_for_scalar(space, w_arg)
else:
return space.interp_w(descriptor.W_Dtype,
space.call_function(space.gettypefor(descriptor.W_Dtype), w_arg))
+
+def as_scalar(space, w_obj):
+ dtype = ufuncs.find_dtype_for_scalar(space, w_obj)
+ return dtype.coerce(space, w_obj)
diff --git a/pypy/module/micronumpy/descriptor.py b/pypy/module/micronumpy/descriptor.py
--- a/pypy/module/micronumpy/descriptor.py
+++ b/pypy/module/micronumpy/descriptor.py
@@ -150,6 +150,9 @@
def is_complex(self):
return self.kind == NPY.COMPLEXLTR
+ def is_number(self):
+ return self.is_int() or self.is_float() or self.is_complex()
+
def is_str(self):
return self.num == NPY.STRING
diff --git a/pypy/module/micronumpy/test/test_ndarray.py b/pypy/module/micronumpy/test/test_ndarray.py
--- a/pypy/module/micronumpy/test/test_ndarray.py
+++ b/pypy/module/micronumpy/test/test_ndarray.py
@@ -4047,3 +4047,9 @@
raises(TypeError, np.can_cast, 'i4', None)
raises(TypeError, np.can_cast, None, 'i4')
+
+ def test_can_cast_scalar(self):
+ import numpy as np
+ assert np.can_cast(127, np.int8)
+ assert not np.can_cast(128, np.int8)
+ assert np.can_cast(128, np.int16)
More information about the pypy-commit
mailing list