Here's a PR with a different dicsussion of __array__:

https://github.com/numpy/numpy/pull/14529

-CHB


On Mon, Sep 16, 2019 at 3:23 PM Chris Barker <chris.barker@noaa.gov> wrote:
OK -- I *finally* got it:

when you pass an arbitrary object into np.asarray(), it will create an array object scalar with the object in it.

So yes, I can see that you may want to raise a TypeError instead, so that users don't get an object array  scalar when they wre expecting to get an array-like object.

So it's probably a good idea to recommend that when a class implements __dauckarray__ that it also implements __array__, which can either raise an exception or return and ndarray.

-CHB


On Mon, Sep 16, 2019 at 3:11 PM Chris Barker <chris.barker@noaa.gov> wrote:
On Mon, Sep 16, 2019 at 2:27 PM Stephan Hoyer <shoyer@gmail.com> wrote:
On Mon, Sep 16, 2019 at 1:45 PM Peter Andreas Entschev <peter@entschev.com> wrote:
What would be the use case for a duck-array to implement __array__ and
return a NumPy array? 
 
Dask arrays are a good example. They will want to implement __duck_array__ (or whatever we call it) because they support duck typed versions of NumPy operation. They also (already) implement __array__, so they can converted into NumPy arrays as a fallback. This is convenient for moderately sized dask arrays, e.g., so you can pass one into a matplotlib function.

Exactly.

And I have implemented __array__ in classes that are NOT duck arrays at all (an image class, for instance). But I also can see wanting to support both:

use me as a duck array
and 
convert me into a proper numpy array.

OK -- looking again at the NEP, I see this suggested implementation:

    def duckarray(array_like):
        if hasattr(array_like, '__duckarray__'):
            return array_like.__duckarray__()
        return np.asarray(array_like)

So I see the point now, if a user wants a duck array -- they may not want to accidentally coerce this object to a real array (potentially expensive).

but in this case, asarray() will only get called (and thus __array__ will only get called), if __duckarray__ is not implemented. So the only reason to impliment __array__ and raise and Exception is so that users will get that exception is the specifically call asarray() -- why should they get that??

I'm working on a PR with suggestion for this.

-CHB

--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

Chris.Barker@noaa.gov


--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

Chris.Barker@noaa.gov


--

Christopher Barker, Ph.D.
Oceanographer

Emergency Response Division
NOAA/NOS/OR&R            (206) 526-6959   voice
7600 Sand Point Way NE   (206) 526-6329   fax
Seattle, WA  98115       (206) 526-6317   main reception

Chris.Barker@noaa.gov