replace elements of vector by condition - matlab

I have got a vector a and a vecor b. And a have bound vectors lb and ub. I want to replace: a[i] = b[i] if lb[i]<b[i]<ub[i]. How should I do it without loops?

M = lb < b & b < ub;
a(M) = b(M);

Related

Inserting matrix into another matrix with Matlab

I want to put a small matrix (p-by-q) called B into a bigger matrix (m-by-n) called A. How can I do it? Matrix B should be put on the right corner of matrix A:
You can do this with basic array indexing, for example:
m = 3;
n = 4;
A = rand(m,n)
p = 2;
q = 3;
B = rand(p,q)
A(end-p+1:end,end-q+1:end) = B
... assuming that p <= m and q <= n of course.

MATLAB replacing some elements from a vector

If i have a vector, lets say L=[10;10;10;11;11;13;13] which is associated to another vector X=[1;6;65;34;21;73;14] and I want to create a third vector, Z, with almost all the elements in X, but just replacing a 0 in X when the element (i,j) from L changes. Lets say that the result that I want should look like this Z=[1;6;65;0;21;0;14]
Any ideas how to solve this?
I would be really thankful :)
That's easy:
X = [1;6;65;34;21;73;14];
L = [10;10;10;11;11;13;13];
Z = X;
ind = [false; diff(L)~=0]; %// logical index of values to be set to 0
Z(ind) = 0;
This works by computing a logical index ind = [false; diff(L)~=0] of the elements where a change has ocurred. The initial false is needed because the first element doesn't have a previous one to compare with. The logical index is used to select which values of Z should be set to 0.
This should work
Z = zeros(length(L))
for i = 2:length(L)
if(L(i-1) == L(i)
Z(i) = X(i);
else
Z(i) = 0;
end
end

How to find an arbitrary perpendicular vector of another vector in MATLAB?

I need to create arbitrary perpendicular vector n with components (a, b, c) to another known vector k with components (x,y,z).
The following code creates arbitrary vector n, but I need random numbers for components in the range [-inf, inf] how can I acheive that? (because otherwise vector components created may not exceed some value in given case 10^11 ) Or maybe concept "arbitrary vector" does not require that?
function [a,b,c] = randomOrghogonalVector(x,y,z)
a = 0;
b = 0;
c = 0;
randomDistr = rand * 10^11 * 2 - 10^11; % issue 1
% excluding trivial solution
if x == 0 && y == 0 && z ==0
a = NaN; b = a; c = a;
else
if z ~=0
a = randomDistr;
b = randomDistr;
c = - (x * a + b * y ) / z;
else
if z == 0 && x ~= 0
c = randomDistr;
b = randomDistr;
a = - (z * c + b * y ) / x;
else
if z == 0 && x == 0 && y ~= 0
c = randomDistr;
a = randomDistr;
b = - (z * c + a * x ) / y;
end
end
end
end
The easiest solution I see is to first find a random vector that is orthogonal to your original vector, and then give it a random length. In Matlab, this can be done by defining the following function
function [a, b, c] = orthoVector(x, y, z)
xin = [x;y;z];
e = xin;
while ((e'*xin)==xin'*xin)
e = 2.*rand(3,1)-1;
end
xout = cross(xin, e);
xout = 1.0/(rand()) * xout;
a = xout(1);
b = xout(2);
c = xout(3);
end
Line-by-line, here's what I'm doing:
you asked for this format [a,b,c] = f(x,y,z). I would recommend using function xout = orthoVector(xin), which would make this code even shorter.
Since Matlab handles vectors best as vectors, I'm creating vector xin.
e will be one random vector, different from xin used to compute the orthogonal vector. Since we're dealing with random vectors, we initialize it to be equal to xin.
For this algorithm to work, we need to make sure that e and xin are pointing in different directions. Until this is the case...
...create a new random vector e. Note that rand will give values between 0 and 1. Thus, each component of e will be between -1 and 1.
Ok, if we end, e and xin are pointing in different directions
Our vector xout will be orthogonal to xin and e.
Let's multiply vector xout by a random number between 1 and "very large"
a is first component of xout
b is second component of xout
c is third component of xout
all done.
Optional: if you want to have very large vectors, you could replace line 8 by
xout = exp(1./rand())/(rand()) * xout;
This will give you a very large spread of values.
Hope this helps, cheers!

How to check whether vector b is in Col A?

How do I determine whether b∈Col A or b∉Col A in matlab? A being an m x n matrix where m >= n, and b being a vector. Is there a built in function for this already, or would I need to create one? If b∈Col A, how would I go about determining whether matrix A has orthonormal columns/is orthogonal?
You can use ismember as explained in a previous answer.
// some sample data
A = [eye(3); zeros(3)];
v = [0; 1; 0; 0; 1; 0];
ismember(A', v', 'rows')
To check orthogonality, you could do the following
// A scalar initialised outside the for-loop. It stores sums of inner products.
dp = 0;
// Take the columns of A one by one and compute the inner product with all subsequent columns. If A is orthogonal, all the inner products have to be zero and, hence, their sum has to be zero.
for i = 1:size(A, 2)
dp = dp + sum(A(:, i)'*A(:, i+1:end));
end
if (dp == 0)
disp('The columns are orthogonal')
else
disp('The columns are not orthogonal')
end
To have orthonormal columns, the norm of each column has to be 1, so:
// Check each column for unit length
M = mat2cell(A, size(A, 1), ones(size(A, 2), 1));
if find(cellfun(#(x)norm(x,2), M) ~= 1)
disp('Columns are not of unit length')
else
disp('Columns are of unit length')
end
Note that all these operations become simpler and faster if m=n (since you allow this case).
Say you have a matrix A that is nxm and a vector b that is nx1, and you want to see if b is a column in A.
You can do this by taking the transpose of both A and b, and then looking to see if the vector b is a member of A. This is the code:
member = ismember(A',b','rows');
Here is an example;
A =
1 5
2 2
3 3
4 4
b =
1
2
3
4
member = ismember(A',b','rows')
member =
1
0
So the first column of A and b are a match but the second column of A and b are not the same. If you want to check the orthogonality of the columns you can do this:
orthcheck = triu(A'*A);
if there are any zeros on the upper triangular matrix then the columns are orthogonal. The A'*A checks the dot product of all the columns and you only need the upper triagular part since the matrix is symmetric.
Another way of testing if v is a column of A:
any(all(bsxfun(#eq,A,v))) %// gives 1 if it is; 0 otherwise
To test if A is orthogonal:
product = A*A'; %'// I'm using ' in case you have complex numbers
product(1:size(A,1)+1:end) = 0; %// remove diagonal
all(product(:)==0) %// gives 1 if it is; 0 otherwise

matlab generate fixed degree undirected graph

I would like to generate the adjacency matrix of an undirected graph with N nodes.
In particular, this graph should have a fixed degree (each node is connected to a fixed number of node d).
If a set d = N-1, the solution is trivial:
A = ones(N) - eye(N);
How can I generalize it for any d?
ADD:
Here is a solution (thanks to Oli Charlesworth):
function A = fixedDegreeGraph(N, d)
A = zeros(N);
for i=1:N
b = i;
f = i;
for k=1:floor(d/2)
f = f + 1;
if (f == N + 1)
f = 1;
end
A(i, f) = 1;
A(f, i) = 1;
b = b - 1;
if (b == 0)
b = N;
end
A(i, b) = 1;
A(b, i) = 1;
end
end
For even d, here's a way to visualise the approach.
Draw the vertices out arranged in a circle.
Each vertex is connected to its immediate (d/2) left-hand neighbours, and its immediate (d/2) right-hand neighbours.
It should be fairly obvious how to turn this into an adjacency matrix (hint: it will be a circulant matrix, so you may find the toeplitz function useful).
Extending this to odd d is not much harder... (although note there is no solution if both N and d are odd)