On Sun, Mar 8, 2009 at 3:02 PM, Darren Dale <dsdal...@gmail.com> wrote:
> On Sun, Mar 8, 2009 at 4:54 PM, Charles R Harris < > charlesr.har...@gmail.com> wrote: > >> >> >> On Sun, Mar 8, 2009 at 2:48 PM, Charles R Harris < >> charlesr.har...@gmail.com> wrote: >> >>> >>> >>> On Sun, Mar 8, 2009 at 1:04 PM, Darren Dale <dsdal...@gmail.com> wrote: >>> >>>> On Sat, Mar 7, 2009 at 1:23 PM, Darren Dale <dsdal...@gmail.com> wrote: >>>> >>>>> On Sun, Feb 22, 2009 at 7:01 PM, Darren Dale <dsdal...@gmail.com>wrote: >>>>> >>>>>> On Sun, Feb 22, 2009 at 6:35 PM, Darren Dale <dsdal...@gmail.com>wrote: >>>>>> >>>>>>> On Sun, Feb 22, 2009 at 6:28 PM, Pierre GM <pgmdevl...@gmail.com>wrote: >>>>>>> >>>>>>>> >>>>>>>> On Feb 22, 2009, at 6:21 PM, Eric Firing wrote: >>>>>>>> >>>>>>>> > Darren Dale wrote: >>>>>>>> >> Does anyone know why __array_wrap__ is not called for subclasses >>>>>>>> >> during >>>>>>>> >> arithmetic operations where an iterable like a list or tuple >>>>>>>> >> appears to >>>>>>>> >> the right of the subclass? When I do "mine*[1,2,3]", array_wrap >>>>>>>> is >>>>>>>> >> not >>>>>>>> >> called and I get an ndarray instead of a MyArray. "[1,2,3]*mine" >>>>>>>> is >>>>>>>> >> fine, as is "mine*array([1,2,3])". I see the same issue with >>>>>>>> >> division, >>>>>>>> > >>>>>>>> > The masked array subclass does not show this behavior: >>>>>>>> >>>>>>>> Because MaskedArray.__mul__ and others are redefined. >>>>>>>> >>>>>>>> Darren, you can fix your problem by redefining MyArray.__mul__ as: >>>>>>>> >>>>>>>> def __mul__(self, other): >>>>>>>> return np.ndarray.__mul__(self, np.asanyarray(other)) >>>>>>>> >>>>>>>> forcing the second term to be a ndarray (or a subclass of). You can >>>>>>>> do >>>>>>>> the same thing for the other functions (__add__, __radd__, ...) >>>>>>> >>>>>>> >>>>>>> Thanks for the suggestion. I know this can be done, but ufuncs like >>>>>>> np.multiply(mine,[1,2,3]) will still not work. Plus, if I reimplement >>>>>>> these >>>>>>> methods, I take some small performance hit. I've been putting a lot of >>>>>>> work >>>>>>> in lately to get quantities to work with numpy's stock ufuncs. >>>>>>> >>>>>> >>>>>> I should point out: >>>>>> >>>>>> import numpy as np >>>>>> >>>>>> a=np.array([1,2,3,4]) >>>>>> b=np.ma.masked_where(a>2,a) >>>>>> np.multiply([1,2,3,4],b) # yields a masked array >>>>>> np.multiply(b,[1,2,3,4]) # yields an ndarray >>>>>> >>>>>> >>>>> I'm not familiar with the numpy codebase, could anyone help me figure >>>>> out where I should look to try to fix this bug? I've got a nice set of >>>>> generators that work with nosetools to test all combinations of numerical >>>>> dtypes, including combinations of scalars, arrays, and iterables of each >>>>> type. In my quantities package, just testing multiplication yields 1031 >>>>> failures, all of which appear to be caused by this bug (#1026 on trak) or >>>>> bug #826. >>>> >>>> >>>> >>>> I finally managed to track done the source of this problem. >>>> _find_array_wrap steps through the inputs, asking each of them for their >>>> __array_wrap__ and binding it to wrap. If more than one input defines >>>> __array_wrap__, you enter a block that selects one based on array priority, >>>> and binds it back to wrap. The problem was when the first input defines >>>> array_wrap but the second one does not. In that case, _find_array_wrap >>>> never >>>> bothered to rebind the desired wraps[0] to wrap, so wrap remains Null or >>>> None, and wrap is what is returned to the calling function. >>>> >>>> I've tested numpy with this patch applied, and didn't see any >>>> regressions. Would someone please consider committing it? >>>> >>>> Thanks, >>>> Darren >>>> >>>> $ svn diff numpy/core/src/umath_ufunc_object.inc >>>> Index: numpy/core/src/umath_ufunc_object.inc >>>> =================================================================== >>>> --- numpy/core/src/umath_ufunc_object.inc (revision 6569) >>>> +++ numpy/core/src/umath_ufunc_object.inc (working copy) >>>> @@ -3173,8 +3173,10 @@ >>>> PyErr_Clear(); >>>> } >>>> } >>>> + if (np >= 1) { >>>> + wrap = wraps[0]; >>>> + } >>>> if (np >= 2) { >>>> - wrap = wraps[0]; >>>> maxpriority = PyArray_GetPriority(with_wrap[0], >>>> PyArray_SUBTYPE_PRIORITY); >>>> for (i = 1; i < np; ++i) { >>>> >>> >>> Applied in r6573. Thanks. >>> >> >> Oh, and can you provide a test for this fix? >> > > > Yes, I'll send a patch for a test as soon as its ready. 6573 closes two > tickets, 1026 and 1022. Did you see the patch I sent for issue #826? It is > also posted at the bug report. > Applied in r6574 <http://projects.scipy.org/numpy/changeset/6574>. I'm not all that familiar with the priority machinery but the patch looked like it wouldn't break anything and since it fixes things for you, in it went. I haven't closed the ticket yet but will do so if you provide some tests. Chuck
_______________________________________________ Numpy-discussion mailing list Numpy-discussion@scipy.org http://mail.scipy.org/mailman/listinfo/numpy-discussion