mathematica help ~ assign each element in a matrix to a value from a column vector - matrix

I have this 4x4 square matrix A, which has a random value in each element. I now have a column matrix (16x1) B which also has random values. The number of values in B is 16 which corresponds to the total number of elements in A.
I am trying to assign the values in B to elements in matrix A in the following way:
A[[1,1]] = B[[1]],
A[[1,2]] = B[[2]],
A[[1,3]] = B[[3]],
A[[1,4]] = B[[4]],
A[[2,1]] = B[[5]],
A[[2,2]] = B[[6]],
A[[2,3]] = B[[7]],
A[[2,4]] = B[[8]],
etc...
Does anyone know a convenient way of doing this so that I can achieve this for any NxN square matrix, and any length M column matrix(Mx1 matrix)? Assuming of course that the total # of elements are the same in both matrices.

If you have Mathematica 9, the function ArrayReshape can turn your list B into an arbitrary m x n Matrix.

Related

Number of submatrix of size AxB in a matrix of size MxN

I am following https://taninamdar.files.wordpress.com/2013/11/submatrices3.pdf to find total number of sub matrix of a matrix.But am stuck how to find how many sub matrix of a given size is present in a matrix.
Also 0<=A<=M and 0<=B<=N.
where AxB(submatrix size) and MxN(matrix size).
I didn't go through the pdf (math and I aren't friends), however simple logic is enough here. Simply, try to reduce the dimension: How many vectors of length m can you put in a vector of length n ?
Answer: n-m+1. To convince you, just go through the cases. Say n = 5 and m = 5. You've got one possibility. With n = 5 and m = 4, you've got two (second vector starts at index 0 or index 1). With n = 5 and m = 3, you've got three (vector can start at index 0, 1 or 2). And for n = 5 and m = 1, you've got 5, seems logic.
So, in order to apply that to a matrix, you have to add a dimension. How do you do that ? Multiplication. How many vectors of length a can you put inside a vector of length n ? n-a+1. How many vectors of length b can you put inside a vector of length m ? m-b+1.
So, how many matrices of size A*B can you put in a matrix of length N*M ? (N-A+1)*(M-B+1).
So, I didn't handle the case where one of the dimension is 0. It depends on how you consider this case.

vectorization of a single loop in matlab (multiplication and then addition)

I have a nX2 matrix A and a 3D matrix K. I would like to take element-wise multiplication specifying 2 indices in 3rd dimension of K designated by each row vector in A and take summation of them.
For instance of a simplified example when n=2,
A=[1 2;3 4];%2X2 matrix
K=unifrnd(0.1,0.1,2,2,4);%just random 3D matrix
L=zeros(2,2);%save result to here
for t=1:2
L=L+prod(K(:,:,A(t,:)),3);
end
Can I get rid of the for loop in this case?
How's this?
B = A.'; %'
L = squeeze(sum(prod(...
reshape(permute(K(:,:,B(:)),[3 1 2]),2,[],size(K,1),size(K,2)),...
1),...
2));
Although your test case is too simple, so I can't be entirely sure that it's correct.
The idea is that we first take all the indices in A, in column-major order, then reshape the elements of K such that the first two dimensions are of size [2, n], and the second two dimensions are the original 2 of K. We then take the product, then the sum along the necessary dimensions, ending up with a matrix that has to be squeezed to get a 2d matrix.
Using a bit more informative test case:
K = rand(2,3,4);
A = randi(4,4,2);
L = zeros(2,3);%save result to here
for t=1:size(A,1)
L = L+prod(K(:,:,A(t,:)),3);
end
B = A.'; %'
L2 = squeeze(sum(prod(reshape(permute(K(:,:,B(:)),[3 1 2]),2,[],size(K,1),size(K,2)),1),2));
Then
>> isequal(L,L2)
ans =
1
With some reshaping magic -
%// Get sizes
[m1,n1,r1] = size(K);
[m2,n2] = size(A);
%// Index into 3rd dim of K; perform reductions and reshape back
Lout = reshape(sum(prod(reshape(K(:,:,A'),[],n2,m2),2),3),m1,n1);
Explanation :
Index into the third dimension of K with a transposed version of A (transposed because we are using rows of A for indexing).
Perform the prod() and sum() operations.
Finally reshape back to a shape same as K but without the third dimension as that was removed in the earlier reduction steps.

Spark distributed matrix multiply and pseudo-inverse calculating

I am very new in Apache Spark Scala. Can you help me with some operations?
I have two distributed matrix H and Y in Spark Scala.
I want to compute the pseudo-inverse of H and then multiply H and Y.
How can I do this?
Here is an implementation for the inverse.
import org.apache.spark.mllib.linalg.{Vectors,Vector,Matrix,SingularValueDecomposition,DenseMatrix,DenseVector}
import org.apache.spark.mllib.linalg.distributed.RowMatrix
def computeInverse(X: RowMatrix): DenseMatrix = {
val nCoef = X.numCols.toInt
val svd = X.computeSVD(nCoef, computeU = true)
if (svd.s.size < nCoef) {
sys.error(s"RowMatrix.computeInverse called on singular matrix.")
}
// Create the inv diagonal matrix from S
val invS = DenseMatrix.diag(new DenseVector(svd.s.toArray.map(x => math.pow(x,-1))))
// U cannot be a RowMatrix
val U = new DenseMatrix(svd.U.numRows().toInt,svd.U.numCols().toInt,svd.U.rows.collect.flatMap(x => x.toArray))
// If you could make V distributed, then this may be better. However its alreadly local...so maybe this is fine.
val V = svd.V
// inv(X) = V*inv(S)*transpose(U) --- the U is already transposed.
(V.multiply(invS)).multiply(U)
}
To calculate the pseudo-inverse of non-square matrices you need to be able to calculate the transpose (easy) and the matrix inverse (others have supplied that functionality). There are two different calculations, depending on whether M has full column rank or full row rank.
Full column rank means that the columns of the matrix are linearly independent which requires that the the number of columns is less than or equal to the number of rows. (In pathological cases, an mxn matrix with m>=n might still not have full column rank, but we'll ignore that statistical impossibility. If it is a possibility in your case, the matrix inversion step below will fail.) For full column rank, the pseudo-inverse is
M^+ = (M^T M)^{-1} M^T
where M^T is the transpose of M. Matrix multiply M^T by M, then take the inverse, then matrix multiply by M^T again. (I'm assuming M has real number entries; if the entries are complex numbers, you also have to take complex conjugates.)
A quick check to make sure you have calculated the psuedo-inverse correctly is to check M^+ M. It should be the identity matrix (up to floating point error).
On the other hand, if M has full row rank, in other words M is mxn with m<=n, the pseudo-inverse is
M^+ = M^T (M M^T)^{-1}
To check whether you have the correct pseudo-inverse in this case, right multiply with the original matrix: M M^+. That should equal the identity matrix, up to floating point error.
Matrix multiplication is the easier one: there are several Matrix implementations with a multiply method in packages org.apache.spark.mllib.linalg and org.apache.spark.mllib.linalg.distributed. Pick whatever fits your needs most.
I have not seen (pseudo-)inverse anywhere in the Spark API. But RowMatrix is able to compute the singular value decomposition which can be used to calculate the inverse of a matrix. Here is a very naive implementation, inspired by How can we compute Pseudoinverse for any Matrix (warning: dimensions of the 2x2 matrix are hard-coded):
val m = new RowMatrix(sc.parallelize(Seq(Vectors.dense(4, 3), Vectors.dense(3, 2))))
val svd = m.computeSVD(2, true)
val v = svd.V
val sInvArray = svd.s.toArray.toList.map(x => 1.0 / x).toArray
val sInverse = new DenseMatrix(2, 2, Matrices.diag(Vectors.dense(sInvArray)).toArray)
val uArray = svd.U.rows.collect.toList.map(_.toArray.toList).flatten.toArray
val uTranspose = new DenseMatrix(2, 2, uArray) // already transposed because DenseMatrix is column-major
val inverse = v.multiply(sInverse).multiply(uTranspose)
// -1.9999999999998297 2.999999999999767
// 2.9999999999997637 -3.9999999999996767
Unfortunately, a lot of conversion from Matrix to Array and so forth is necessary. If you need a fully distributed implementation, try using DistributedMatrix instead of DenseMatrix. If not, maybe using Breeze is preferable here.

Generating a random matrix with non-static constraints

I would like to generate a random matrix with constraints on both rows and columns in MATLAB. But the problem is I have two parameters for this constraints which are not fix for each element. For explanation, consider the mxn matrix P = [P1 ; P2; ...; Pm], and 2 other vectors lambda and Mu with m and n elements, respectively.
Consider lambda as [lambda(1), lambda(2), ..., lambda(m)] and Mu as [Mu(1), Mu2, ..., Mu(n)]
lamda and Mu should have this constraints:
sum of lambda(s) < sum of Mu(s).
,Now for the random matrix P:
each element of the matrix(P[j,i]) should be equal or greater than zero.
sum of the elements of each row is equal to one (i.e. for the row of j: sigma_i(P[j,i] = 1)
for each column j, sum of the production of each element with the correspond lambda(j) is less than the correspond element in the Mu vector (i.e.Mu(i)). i.e. for the column of i: sigma_j(P[j,i]*lambda(j)) < Mu(i)
I have tried coding all these constraints but because the existence of lambda and Mu vectors, just one of the constraints of 3 or 4 can be feasible. May you please help me for coding this matrix.
Thanks in advance
There could be values of Mu and Lambda that does not allow any value of P[i,j].
For each row-vector v:
Constraint 3 means the values are constrained to the hyper-plane v.1 = 1 (A)
Constraint 4 means the values are constrained to the half-space v.Lambda < m (H), where m is the element of Mu corresponding to the current row.
Constraint 1 does not guarantee that these two constraint generates a non-empty solution space.
To verify that the solution-space is non-empty, the easiest method is by checking each corner of hyper-plane A (<1,0,0,...>, <0,1,0,...>, ...). If at least one of the corners qualify for constraint 4, the solution-space is non-empty.
Having said that; Assuming the solution-space is non-empty, you could generate values matching those constraints by:
Generate random vector with elements 0 ≤ vi ≤ 1.
Scale by dividing by the sum of the elements.
If this vector does not qualify for constraint 4, repeat from step 1.
Once you have n such vectors, combine them as rows into a matrix.
The speed of this algorithm depends on how large volume of hyper-plane A is contained inside the half-space H. If only 1% is contained, it would expected to require 100 iterations for that row.

choosing row m from two matrices at random

I have two m*n matrices, A and P. I want to randomly choose the same 3 rows from both matrices, e.g. rows m, m+1, m+2 are picked from both matrices. I want to be able to make the calculation U=A-P on the selected subset (i.e. Usub-Psub), rather than before the selection. So far I have only been able to select rows from one matrix, without being able to match it to the other. The code I use for this is:
A=[0,1,1,3,2,4,4,5;0,2,1,1,3,3,5,5;0,3,1,1,4,4,2,5;0,1,1,1,2,2,5,5]
P=[0,0,0,0,0,0,0,0;0,0,0,0,0,0,0,0;0,0,0,0,0,0,0,0;0,0,0,0,0,0,0,0]
U=A-P
k = randperm(size(U,1));
Usub = U(k(1:3),:);
I would first create a function that returned a submatrix that had only three rows in it that takes an integer as the first of the three row. Then i'd do something like this:
m = number of rows;
randomRow = rand() % m;
U = A.sub(randomRow) - P.sub(randomRow);

Resources