Author: Alex Gaynor <alex.gay...@gmail.com> Branch: Changeset: r46935:2e6d40cabec2 Date: 2011-08-30 21:44 -0400 http://bitbucket.org/pypy/pypy/changeset/2e6d40cabec2/
Log: Max numpy.array.{max,min} use the maximum/minimum ufuncs. diff --git a/pypy/module/micronumpy/interp_numarray.py b/pypy/module/micronumpy/interp_numarray.py --- a/pypy/module/micronumpy/interp_numarray.py +++ b/pypy/module/micronumpy/interp_numarray.py @@ -97,29 +97,8 @@ descr_sum = _reduce_ufunc_impl("add") descr_prod = _reduce_ufunc_impl("multiply") - - def _reduce_max_min_impl(op_name): - reduce_driver = jit.JitDriver(greens=['signature'], - reds = ['i', 'size', 'self', 'result', 'dtype']) - def loop(self, result, size): - i = 1 - dtype = self.find_dtype() - while i < size: - reduce_driver.jit_merge_point(signature=self.signature, - self=self, dtype=dtype, - size=size, i=i, result=result) - result = getattr(dtype, op_name)(result, self.eval(i)) - i += 1 - return result - - def impl(self, space): - size = self.find_size() - if size == 0: - raise OperationError(space.w_ValueError, - space.wrap("Can't call %s on zero-size arrays" \ - % op_name)) - return loop(self, self.eval(0), size).wrap(space) - return func_with_new_name(impl, "reduce_%s_impl" % op_name) + descr_max = _reduce_ufunc_impl("maximum") + descr_min = _reduce_ufunc_impl("minimum") def _reduce_argmax_argmin_impl(op_name): reduce_driver = jit.JitDriver(greens=['signature'], @@ -175,8 +154,6 @@ def descr_any(self, space): return space.wrap(self._any()) - descr_max = _reduce_max_min_impl("max") - descr_min = _reduce_max_min_impl("min") descr_argmax = _reduce_argmax_argmin_impl("max") descr_argmin = _reduce_argmax_argmin_impl("min") diff --git a/pypy/module/micronumpy/interp_ufuncs.py b/pypy/module/micronumpy/interp_ufuncs.py --- a/pypy/module/micronumpy/interp_ufuncs.py +++ b/pypy/module/micronumpy/interp_ufuncs.py @@ -1,5 +1,5 @@ from pypy.interpreter.baseobjspace import Wrappable -from pypy.interpreter.error import OperationError +from pypy.interpreter.error import OperationError, operationerrfmt from pypy.interpreter.gateway import interp2app from pypy.interpreter.typedef import TypeDef, GetSetProperty, interp_attrproperty from pypy.module.micronumpy import interp_dtype, signature @@ -41,28 +41,36 @@ from pypy.module.micronumpy.interp_numarray import convert_to_array, Scalar if self.argcount != 2: - raise OperationError(space.w_ValueError, space.wrap("reduce only supported for binary functions")) - if self.identity is None: - raise OperationError(space.w_NotImplementedError, space.wrap("%s is missing its identity value" % self.name)) + raise OperationError(space.w_ValueError, space.wrap("reduce only " + "supported for binary functions")) assert isinstance(self, W_Ufunc2) obj = convert_to_array(space, w_obj) if isinstance(obj, Scalar): - raise OperationError(space.w_TypeError, space.wrap("cannot reduce on a scalar")) + raise OperationError(space.w_TypeError, space.wrap("cannot reduce " + "on a scalar")) size = obj.find_size() dtype = find_unaryop_result_dtype( space, obj.find_dtype(), promote_to_largest=True ) - value = self.identity.convert_to(dtype) + start = 0 + if self.identity is None: + if size == 0: + raise operationerrfmt(space.w_ValueError, "zero-size array to " + "%s.reduce without identity", self.name) + value = obj.eval(0).convert_to(dtype) + start += 1 + else: + value = self.identity.convert_to(dtype) new_sig = signature.Signature.find_sig([ self.reduce_signature, obj.signature ]) - return self.reduce(new_sig, value, obj, dtype, size).wrap(space) + return self.reduce(new_sig, start, value, obj, dtype, size).wrap(space) - def reduce(self, signature, value, obj, dtype, size): - i = 0 + def reduce(self, signature, start, value, obj, dtype, size): + i = start while i < size: reduce_driver.jit_merge_point(signature=signature, self=self, value=value, obj=obj, i=i, diff --git a/pypy/module/micronumpy/test/test_ufuncs.py b/pypy/module/micronumpy/test/test_ufuncs.py --- a/pypy/module/micronumpy/test/test_ufuncs.py +++ b/pypy/module/micronumpy/test/test_ufuncs.py @@ -305,6 +305,9 @@ raises(TypeError, add.reduce, 1) def test_reduce(self): - from numpy import add + from numpy import add, maximum - assert add.reduce([1, 2, 3]) == 6 \ No newline at end of file + assert add.reduce([1, 2, 3]) == 6 + assert maximum.reduce([1]) == 1 + assert maximum.reduce([1, 2, 3]) == 3 + raises(ValueError, maximum.reduce, []) \ No newline at end of file diff --git a/pypy/module/micronumpy/test/test_zjit.py b/pypy/module/micronumpy/test/test_zjit.py --- a/pypy/module/micronumpy/test/test_zjit.py +++ b/pypy/module/micronumpy/test/test_zjit.py @@ -90,14 +90,21 @@ def test_max(self): space = self.space float64_dtype = self.float64_dtype + int64_dtype = self.int64_dtype def f(i): - ar = SingleDimArray(i, dtype=NonConstant(float64_dtype)) + if NonConstant(False): + dtype = int64_dtype + else: + dtype = float64_dtype + ar = SingleDimArray(i, dtype=dtype) j = 0 while j < i: ar.get_concrete().setitem(j, float64_dtype.box(float(j))) j += 1 - return ar.descr_add(space, ar).descr_max(space).floatval + v = ar.descr_add(space, ar).descr_max(space) + assert isinstance(v, FloatObject) + return v.floatval result = self.meta_interp(f, [5], listops=True, backendopt=True) self.check_loops({"getarrayitem_raw": 2, "float_add": 1, @@ -109,14 +116,21 @@ def test_min(self): space = self.space float64_dtype = self.float64_dtype + int64_dtype = self.int64_dtype def f(i): - ar = SingleDimArray(i, dtype=NonConstant(float64_dtype)) + if NonConstant(False): + dtype = int64_dtype + else: + dtype = float64_dtype + ar = SingleDimArray(i, dtype=dtype) j = 0 while j < i: ar.get_concrete().setitem(j, float64_dtype.box(float(j))) j += 1 - return ar.descr_add(space, ar).descr_min(space).floatval + v = ar.descr_add(space, ar).descr_min(space) + assert isinstance(v, FloatObject) + return v.floatval result = self.meta_interp(f, [5], listops=True, backendopt=True) self.check_loops({"getarrayitem_raw": 2, "float_add": 1, _______________________________________________ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit