I'm wondering if there is a simple way to multiply a numpy matrix by a scalar. Essentially I want all values to be multiplied by the constant 40. This would be an nxn matrix with 40's on the diagonal, but I'm wondering if there is a simpler function to use to scale this matrix. Or how would I go about making a matrix with the same shape as my other matrix and fill in its diagonal?
Sorry if this seems a bit basic, but for some reason I couldn't find this in the doc.
If you want a matrix with 40 on the diagonal and zeros everywhere else, you can use NumPy's function fill_diagonal() on a matrix of zeros. You can thus directly do:
N = 100; value = 40
b = np.zeros((N, N))
np.fill_diagonal(b, value)
This involves only setting elements to a certain value, and is therefore likely to be faster than code involving multiplying all the elements of a matrix by a constant. This approach also has the advantage of showing explicitly that you fill the diagonal with a specific value.
If you want the diagonal matrix b to be of the same size as another matrix a, you can use the following shortcut (no need for an explicit size N):
b = np.zeros_like(a)
np.fill_diagonal(b, value)
Easy:
N = 100
a = np.eye(N) # Diagonal Identity 100x100 array
b = 40*a # Multiply by a scalar
If you actually want a numpy matrix vs an array, you can do a = np.asmatrix(np.eye(N)) instead. But in general * is element-wise multiplication in numpy.
Related
I'm trying to make a matrix/vector multiplication, but my matrix is stored in a way # operator cannot be used.
My matrix Z is actually a list on size N containing the columns of the matrix which are all PETSc4py.Vec of size NN, where NN≫N (eg. NN=10000 and N=10). As N is small, I can make a for loop on it, so for instance, if I want to compute r =Z.T # u with u a vector of size NN, I do
r = np.zeros(N)
for i,z in enumerate(Z):
r[i] = u * z # scalar product
Now I have a vector u of size N and I want to make the multiplication w = Z # u, I can't apply the same method because it would involve a loop of size NN which I'm trying to avoid.
I could convert my "matrix" Z to a NumPy matrix, but I'm also trying to avoid it...
I represented on the figure 1 the way the matrix is stored. A red line represents a vector that should be read for a the matrix-vector multiplication.
Is there a mathematical way (or a magic trick !) to compute this operation without making the big loop ?
Thanks
I wanted to define my own addition operator that takes an Nx1 vector (call it A) and a 1xN vector (B) such that the element in the i^th row and j^th column is the sum of the i^th element in A and the j^th element in B. An example is illustrated here.
I was able to write the following code for the function (and it is correct as far as I know).
def test_fn(a, b):
a_len = a.shape[0]
b_len = b.shape[1]
prod = np.array([[0]*a_len]*b_len)
for i in range(a_len):
for j in range(b_len):
prod[i, j] = a[i, 0] + b[0, j]
return prod
However, the vectors I am working with contain thousands of elements, and the function above is quite slow. I was wondering if there was a better way to approach this problem, or if there was a numpy function that could be of use. Any help would be appreciated.
According to numpy's broadcasting rules, you can use a+b to implement your own defined operator.
The first rule of broadcasting is that if all input arrays do not have the same number of dimensions, a “1” will be repeatedly prepended to the shapes of the smaller arrays until all the arrays have the same number of dimensions.
The second rule of broadcasting ensures that arrays with a size of 1 along a particular dimension act as if they had the size of the array with the largest shape along that dimension. The value of the array element is assumed to be the same along that dimension for the “broadcast” array.
For example, I have an equation for projection matrix which works for 1 dimensional vectors:
where P is projection matrix and T is transpose.
We know that we can't simplify this fraction more (by cancelling terms) since denominator is a dot product (thus 0 dimensional scalar, number) and numerator is a matrix (column multiplied by row is a matrix).
I'm not sure how could I define function for this equation in numpy, considering that the current function that I'm using does not differentiate between these terms, multiplication is treated as it has commutative property. I'm using numpy.multiply method:
>>> import numpy as np
>>> a = np.array(a)
>>> a*a.T
array([1, 4, 9])
>>> a.T*a
array([1, 4, 9])
As you see, both of them output vectors.
I've also tried using numpy.matmul method:
>>> np.matmul(a, a.T)
14
>>> np.matmul(a.T, a)
14
which gives dot product for both of the function calls.
I also did try numpy.dot but it obviously doesn't work for numerator terms.
From my understanding, the first function call should output matrix (since column is multiplied by row) and the second function call should output a scalar in a proper case.
Am I mistaken? Is there any method that differentiates between a multiplied by a transpose and a transpose multiplied by a?
Thank you!
Note that 1-dimensional numpy arrays are not column vectors (and operations such as transposition do not make sense). If you want to obtain a column vector you should define your array as a 2-dimensional array (with the second dimension size equal to 1).
However, you don't need to define a column vector, as numpy offers functions to do what you want by manipulating an 1D array as follows
P = np.outer(a,a)/np.inner(a,a)
Stelios' answer is the best, no doubt but for completeness you can use the # operator with 2-d arrays:
a = np.array([1,4,9])[np.newaxis]
P = (a.T # a) / (a # a.T)
I have a matrix A with size (5,7,3) and a matrix B with size (5,3,8). I want to multiply them C = A.B, and the size of C is (5,7,8).
It means that one 2D submatrix with size (7,3) in matrix A will be multiplied with one 2D submatrix with size (3,8) in matrix B respectively. So I have to multiply 5 times.
The simplest way is using a loop and numpy:
for u in range(5):
C[u] = numpy.dot(A[u],B[u])
Is there any way to do this without using a loop?
Is there any equivalent method in Theano to do this without using scan?
Can be done pretty simply with np.einsum in numpy.
C = numpy.einsum('ijk,ikl->ijl', A, B)
It can also simply be:
C = numpy.matmul(A,B)
Since the docs state:
If either argument is N-D, N > 2, it is treated as a stack of matrices residing in the last two indexes and broadcast accordingly
Theano has similar functionaly of batched_dot so it would be
C = theano.tensor.batched_dot(A, B)
in a current project I have a large multidimensional array of shape (I,J,K,N) and a square matrix of dim N.
I need to perform a matrix vector multiplication of the last axis of the array with the square matrix.
So the obvious solution would be:
for i in range(I):
for j in range(J):
for k in range(K):
arr[i,j,k] = mat.dot(arr[i,j,k])
but of course this is rather slow. So I also tried numpy's tensordot but had little success.
I would expect that something like:
arr = tensordot(mat,arr,axes=((0,1),(3)))
should do the trick but I get a shape mismatch error.
Has someone a better solution or knows how to correctly use tensordot?
Thank you!
This should do what your loops, but with vectorized looping:
from numpy.core.umath_tests import matrix_multiply
arr[..., np.newaxis] = matrix_multiply(mat, arr[..., np.newaxis])
matrix_multiply and its sister inner1d are hidden, undocumented, gems of numpy, although a full set of linear algebra gufuncs should see the light with numpy 1.8. matrix_multiply does matrix multiplication on the last two dimensions of its inputs, and broadcasting on the rest. The only tricky part is setting an additional dimension, so that it sees column vectors when multiplying, and adding it also on assignment back into array, so that there is no shape mismatch.
I think your for loop is wrong, and for this case dot seems to be enough:
# a is your IJKN
# b is your NN
c = dot(a, b)
Here c will be a IJKN array. If you want to sum over the last dimension to get the IJK array:
arr = dot(a,b).sum(axis=3)
BUT I'm NOT SURE IF THIS IS WHAT YOU WANT...