Histogram on elements of a 2D matrix in Matlab - matlab

I am wondering if there is any build in function or an easy way to plot a histogram of elements of a 2d array.
For example, if A=rand(100,1), then A is an 1D array, and hist(A) can do the histogram.
However, what if A=rand(100,100), and I would like to make a histogram on elements of A, just like treating each element in A as an element on a 1D array. Is there a easy way to do so?

You just have to reshape A into a vector, then you can use hist as usual:
hist(A(:))

This command will do what you want:
hist(reshape(A, prod(size(A)), 1))
What it does is create a vector out of the matrix A by reshaping it into a matrix with one column and a number of rows equal to the number of elements of A:
prod(size(A)) = number_of_columns(A) * number_of_rows(A)
Or the short way:
hist(A(:))
This takes every element of A in sequence and thus also generates a vector.

Related

mathematical operation (Sum) on array elements

I want to sum elements of array which every element is a matrix.
I wrote below but not working:
AA={[1 2;3 4],[5 6;7 8]}
i=1:2;
sum(AA{i})
If you are wanting to perform operations across a set of 2-D matrices, all of which are the same size (and not too huge), it's easiest to store them as a 3-D matrix instead. See here for discussion/examples.
If you already have your matrices in a cell array, as in your example, you can concatenate them into a 3-D matrix using cat and sum across the third dimension without a for loop using sum:
mat = sum(cat(3, AA{:}), 3);

Selecting the vector with the largest sum Matlab

I'm looking for a way to select the vector that has the largest sum. Is there a simple way of doing this? I was thinking of writing a loop, but I'm not sure how to loop over a set of vectors.
Thanks for your help!
For the case in which the vectors have the same length (as stated in the comment), I think a simple loop-free way would be to build a matrix from each vector and fetch directly the row (or column) with the largest sum:
clear
clc
RandMat = rand(8,10);
[~,Ind] = max(sum(RandMat,2)); %// Get row index for largest sum. If you want the column, use 1 instead.
MaxRow = RandMat(Ind,:); %// Index in original matrix to get the vector. If you want the column, use RandMat(:,Ind);
If vectors don't have the same length then you would need to pad the missing values with NaN for example to use a regular matrix, otherwise you would need a cell array.
If you prefer a solution in which you don't have to build a matrix then you could loop through each individual vector and store the sum in a variable, then compare the sums at the end. If you would like such a solution please ask!

Matlab 3d-matrix

I have to create a very big 3D matrix (such as: 500000x60x60). Is there any way to do this in matlab?
When I try
omega = zeros(500000,60,60,'single');
I get an out-of-memory error.
The sparse function is no option since it is only meant for 2D matrices. So is there any alternative to that for higher dimensional matrices?
Matlab only has support for sparse matrices (2D). For 3D tensors/arrays, you'll have to use a workaround. I can think of two:
linear indexing
cell arrays
Linear indexing
You can create a sparse vector like so:
A = spalloc(500000*60*60, 1, 100);
where the last entry (100) refers to the amount of non-zeros eventually to be assigned to A. If you know this amount beforehand it makes memory usage for A more efficient. If you don't know it beforehand just use some number close to it, it'll still work, but A can consume more memory in the end than it strictly needs to.
Then you can refer to elements as if it is a 3D array like so:
A(sub2ind(size(A), i,j,k))
where i, j and k are the indices to the 1st, 2nd and 3rd dimension, respectively.
Cell arrays
Create each 2D page in the 3D tensor/array as a cell array:
a = cellfun(#(x) spalloc(500000, 60, 100), cell(60,1), 'UniformOutput', false);
The same story goes for this last entry into spalloc. Then concatenate in 3D like so:
A = cat(3, a{:});
then you can refer to individual elements like so:
A{i,j,k}
where i, j and k are the indices to the 1st, 2nd and 3rd dimension, respectively.
Since your matrix is sparse, try to use ndsparse (N-dimensional sparse arrays FEX)

dynamic output for ndgrid in Matlab

I'd like to generate indices for an n-dimensional array with ndgrid. Since the dimension may change, is there a way to wrap ndgrid so that the number of outputs for ndgrid is dynamic? Say for example, I want the output for a 2 dimension array to be:
[output{1} output{2}]=ndgrid(1:5)
and the output for a 3 dimension array to be:
[output{1} output{2} output{3}]=ndgrid(1:5)
so on and so forth...
If you want different sizes for the different dimensions, you might want to consider something like:
creating adjacency matrix.
The relevant part is:
ndim = numel(sz);
I=cell(ndim,1);
% construct the neighborhood
for di=1:ndim
I{di}=1:sz(di);
end
[I{1:ndim}]=ndgrid(I{:});

Matlab: Getting a list of vectors

I have a single row matrix theta in Matlab with a couple hundred values; I would like to create a vector for each value in theta. Preferably I can simply store these values in a list so I can take dot products of individual elements in the list lator; how would I go about doing this?
For now, the code I have is
arrayfun(#(x) [sin(x),0,cos(x)],thetas,'UniformOutput',false);
which generates a bunch of [1x3 double]'s.
Instead of creating a cell array, you can also just create a numeric array of size numberOfThetas-by-3, like so:
A = [sin(thetas);zeros(size(thetas));cos(thetas)]'; %'# make n-by-3 by transposing
To calculate the dot product between any two vectors i and j, you can write
dotProduct = sum(A(i,:).*A(j,:));
You don't have to unnecessarily construct for loops to re-build the matrix as suggested by strictlyrude27. There is a nice inbuilt function cell2mat that does this for you in a single line.
Say your A is a 100 element cell, each of which holds a 1x3 vector. If you wanted to collect them such that each cell of A is a separate row, the command is simply
matrixA = cell2mat(A(:));
The output to your code is a cell array, whose elements are the 1x3 vectors you wanted. So suppose you assigned A = arrayfun(#(x) [sin(x),0,cos(x)],thetas,'UniformOutput',false); as you have up there. The vector corresponding with the ith element of array thetas may be accessed with A{i}. At this point you could use a for loop to construct a matrix whose ith column is the vector corresponding to the ith element of thetas.