Hi! I am trying to use the "dot" method on multi-(more than 2)-dimensional arrays. Specifically I do >> y = dot(a, b) where a is a 2D array and b is a 3D array. using numpy I get the the help: " dot(...) dot(a,v) returns matrix-multiplication between a and b. The product-sum is over the last dimension of a and the second-to-last dimension of b. " I then expect that >> y[i, j, k] = sum(a[i, :] * b[j, :, k]) which is actually what I get. The question is then: 1) Is there any way to change the axis for which the product-sum is performed. This can of course be done by a swapaxis before and after the operation, but this makes the array non-contiguous, in which case the dot operation often makes bugs (at least in Numeric). 2) For complicated reasons we still use Numeric in our software package, and in this, "dot" behaves very strangely. According to the Numeric help: " dot(a, b) dot(a,b) returns matrix-multiplication between a and b. The product-sum is over the last dimension of a and the second-to-last dimension of b. " so I would have expected again that y[i, j, k] = sum(a[i, :] * b[j, :, k]), and the dimensions actually fit, i.e. y.shape = (a.shape[0], b.shape[0], b.shape[2]), but only some rows of the result has these values!! Does anyone know what Numeric.dot(a, b) actually does when b has more than two dimensions? I use the following test script: ---------------------BEGIN SCRIPT----------------------- import Numeric as num # import numpy as num # make 'random' input arrays a = num.zeros((2, 5)) b = num.zeros((3, 5, 4)) a.flat[:] = num.arange(len(a.flat)) - 3 b.flat[:] = num.arange(len(b.flat)) + 5 # built-in dot product y1 = num.dot(a, b) # manual dot product y2 = num.zeros((a.shape[0], b.shape[0], b.shape[2])) for i in range(a.shape[0]): for j in range(b.shape[0]): for k in range(b.shape[2]): y2[i, j, k] = num.sum(a[i,:] * b[j, :, k]) # test for consistency print y1 == y2 ---------------------END SCRIPT------------------------ with the result: [[[1 1 1 1] [0 0 0 0] [0 0 0 0]] [[1 1 1 1] [0 0 0 0] [0 0 0 0]]] thanks a lot, Carsten Rostgaard Carsten.Rostgaard@fysik.dtu.dk
On 11/23/06, Carsten Rostgaard <Carsten.Rostgaard@fysik.dtu.dk> wrote:
Hi! I am trying to use the "dot" method on multi-(more than 2)-dimensional arrays.
Specifically I do >> y = dot(a, b) where a is a 2D array and b is a 3D array.
using numpy I get the the help: " dot(...) dot(a,v) returns matrix-multiplication between a and b. The product-sum is over the last dimension of a and the second-to-last dimension of b. " I then expect that >> y[i, j, k] = sum(a[i, :] * b[j, :, k]) which is actually what I get.
The question is then: 1) Is there any way to change the axis for which the product-sum is performed. This can of course be done by a swapaxis before and after the operation, but this makes the array non-contiguous, in which case the dot operation often makes bugs (at least in Numeric). 2) For complicated reasons we still use Numeric in our software package, and in this, "dot" behaves very strangely. According to the Numeric help:
In Numpy tensordot(a, b, axes=2) tensordot returns the product for any (ndim >= 1) arrays. r_{xxx, yyy} = \sum_k a_{xxx,k} b_{k,yyy} where the axes to be summed over are given by the axes argument. the first element of the sequence determines the axis or axes in arr1 to sum over, and the second element in axes argument sequence determines the axis or axes in arr2 to sum over. When there is more than one axis to sum over, the corresponding arguments to axes should be sequences of the same length with the first axis to sum over given first in both sequences, the second axis second, and so forth. If the axes argument is an integer, N, then the last N dimensions of a and first N dimensions of b are summed over. I don't know about numeric. Chuck
Hi,
The question is then: 1) Is there any way to change the axis for which the product-sum is performed. This can of course be done by a swapaxis before and after the operation, but this makes the array non-contiguous, in which case the dot operation often makes bugs (at least in Numeric). 2) For complicated reasons we still use Numeric in our software package, and in this, "dot" behaves very strangely.
The behaviour for >2D arrays has a bug which was fixed for numpy long ago. (I was the one who found it. :-)) It lead exactly to the behaviour you found (first row is correct, rest is garbage). I do not know if it was fixed in Numeric, maybe updating to the latest version will help. Otherwise, maybe the best workaround is to use a for loop and calculate dot elementwise. Johannes
participants (3)
-
Carsten Rostgaard
-
Charles R Harris
-
Johannes Loehnert