<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Thu, Aug 28, 2014 at 5:40 PM, Nathaniel Smith <span dir="ltr"><<a href="mailto:njs@pobox.com" target="_blank">njs@pobox.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">


<div><div><span style="color:rgb(34,34,34)">Some thoughts:</span><br></div></div>
<br>
But, for your computed dimension idea I'm wondering if what we should<br>
do instead is just let a gufunc provide a C callback that looks at the<br>
input array dimensions and explicitly says somehow which dimensions it<br>
wants to treat as the core dimensions and what its output shapes will<br>
be. There's no rule that we have to extend the signature mini-language<br>
to be Turing complete, we can just use C :-).<br>
<br>
It would be good to have a better motivation for computed gufunc<br>
dimensions, though. Your "all pairwise cross products" example would<br>
be *much* better handled by implementing the .outer method for binary<br>
gufuncs: pairwise_cross(a) == cross.outer(a, a). This would make<br>
gufuncs more consistent with ufuncs, plus let you do<br>
all-pairwise-cross-products between two different sets of cross<br>
products, plus give us all-pairwise-matrix-products for free, etc.<br></blockquote><div><br></div><div>The outer for binary gufuncs sounds like a good idea. A reduce for binary gufuncs that allow it (like square matrix multiplication) would also be nice. But going back to the original question, the pairwise whatevers were just an example: one could come up with several others, e.g.:</div>

<div><br></div><div>    (m),(n)->($p),($q) with $p = m - n and $q = n - 1, could be (I think) the signature of a polynomial division gufunc</div>
<div>    (m),(n)->($p), with $p = m - n + 1, could be the signature of a convolution or correlation gufunc</div><div>    (m)->($n), with $n = m / 2, could be some form of downsampling gufunc</div><div> <br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">



While you're messing around with the gufunc dimension matching logic,<br>
any chance we can tempt you to implement the "optional dimensions"<br>
needed to handle '@', solve, etc. elegantly? The rule would be that<br>
you can write something like<br>
   (n?,k),(k,m?)->(n?,m?)<br>
and the ? dimensions are allowed to take on an additional value<br>
"nothing at all". If there's no dimension available in the input, then<br>
we act like it was reshaped to add a dimension with shape 1, and then<br>
in the output we squeeze this dimension out again. I guess the rules<br>
would be that (1) in the input, you can have ? dimensions at the<br>
beginning or the end of your shape, but not both at the same time, (2)<br>
any dimension that has a ? in one place must have it in all places,<br>
(3) when checking argument conformity, "nothing at all" only matches<br>
against "nothing at all", not against 1; this is because if we allowed<br>
(n?,m),(n?,m)->(n?,m) to be applied to two arrays with shapes (5,) and<br>
(1, 5), then it would be ambiguous whether the output should have<br>
shape (5,) or (1, 5).<br></blockquote><div><br></div><div>I definitely do not mind taking a look into it. I need to think a little more about the rules to convince myself that there is a consistent set of them that we can use. I also thought there may be a performance concern, that you may want to have different implementations when dimensions are missing, not automatically add a 1 and then remove it. It doesn't seem to be the case with neither `np.dot` nor `np.solve`, so maybe I am being overly cautious.</div>

<div><br></div><div>Thanks for your comments and ideas. I have a feeling there are some nice features hidden in here, but I can't seem to figure out what should they be on my own.</div><div><br></div><div>Jaime</div>
<div>
<br></div></div>-- <br>(\__/)<br>( O.o)<br>( > <) Este es Conejo. Copia a Conejo en tu firma y ayúdale en sus planes de dominación mundial.
</div></div>