find all possible element combinations containing the last element in matlab - matlab

I have a vector [x1, x2,...xn]. Is there a way to find all possible combinations of elements that contain the last element xn? For example, if I have 4 elements I want the combinations:
x1,x4
x2,x4
x3,x4
x1,x2,x3,x4
x1,x2,x4
x1,x3,x4
x2,x3,x4
In reality though I have number of elements up to a few hundreds.
Thank you for your time!

You really just need to do a choose on all of the elements except the last one.
C = cell(length(x)-1,1);
for n = 1:length(x)-1
C{n} = nchoosek(x(1:end-1),n);
end
Each element of C contains all possible vectors with n elements. All you have to do is tack onx(end) to each one to get what you're looking for. For example, if combo=C{4}(7,:) is one solved set without the last element of x, then your desired output is combo=[combo x(end)]. To do this for all solutions, just add this line of code inside the loop above:
C{n} = [C{n} x(end)*ones(size(C{n},1),1)];
WARNING: With thousands of elements you will run out of memory very quickly. Just 100 elements gives you over 6e29 possible combinations!

Related

Build a matrix starting from instances of structure fields in MATLAB

I'm really sorry to bother so I hope it is not a silly or repetitive question.
I have been scraping a website, saving the results as a collection in MongoDB, exporting it as a JSON file and importing it in MATLAB.
At the end of the story I obtained a struct object organised
like this one in the picture.
What I'm interested in are the two last cell arrays (which can be easily converted to string arrays with string()). The first cell array is a collection of keys (think unique products) and the second cell array is a collection of values (think prices), like a dictionary. Each field is an instance of possible values for a set of this keys (think daily prices). My goal is to build a matrix made like this:
KEYS VALUES_OF_FIELD_1 VALUES_OF_FIELD2 ... VALUES_OF_FIELDn
A x x x
B x z NaN
C z x y
D NaN y x
E y x z
The main problem is that, as shown in the image and as I tried to explain in the example matrix, I don't always have a value for all the keys in every field (as you can see sometimes they are 321, other times 319 or 320 or 317) and so the key is missing from the first array. In that case I should fill the missing value with a NaN. The keys can be ordered alphabetically and are all unique.
What would you think would be the best and most scalable way to approach this problem in MATLAB?
Thank you very much for your time, I hope I explained myself clearly.
EDIT:
Both arrays are made of strings in my case, so types are not a problem (I've modified the example). The main problem is that, since the keys vary in each field, firstly I have to find all the (unique) keys in the structure, to build the rows, and then for each column (field) I have to fill the values putting NaN where the key is missing.
One thing to remember you can't simply use both strings and number in one matrix. So, if you combine them together they can be either all strings or all numbers. I think all strings will work for you.
Before make a matrix make sure that all the cells have same element.
new_matrix = horzcat(keys,values1,...valuesn);
This will provide a matrix for each row (according to your image). Now you can use a for loop to get matrices for all the rows.
For now, I've solved it by considering the longest array of keys in the structure as the complete set of keys, let's call it keys_set.
Then I've created for each field in the structure a Map object in this way:
for i=1:length(structure)
structure(i).myMap = containers.Map(structure(i).key_field, structure(i).value_field);
end
Then I've built my matrix (M) by checking every map against the keys_set array:
for i=1:length(keys_set)
for j=1:length(structure)
if isKey(structure(j).myMap,char(keys_set(i)))
M(i,j) = string(structure(j).myMap(char(keys_set(i))));
else
M(i,j) = string('MISSING');
end
end
end
This works, but it would be ideal to also be able to check that keys_set is really complete.
EDIT: I've solved my problem by using this function and building the correct set of all the possible keys:
%% Finding the maximum number of keys in all the fields
maxnk = length(structure(1).key_field);
for i=2:length(structure)
if length(structure(i).key_field) > maxnk
maxnk = length(structure(i).key_field);
end
end
%% Initialiting the matrix containing all the possibile set of keys
keys_set=string(zeros(maxnk,length(structure)));
%% Filling the matrix by putting "0" if the dimension is smaller
for i=1:length(structure)
d = length(string(structure(i).key_field));
if d == maxnk
keys_set(:,i) = string(structure(i).key_field);
else
clear tmp
tmp = [string(structure(i).key_field); string(zeros(maxnk-d,1))];
keys_set(:,i) = tmp;
end
end
%% Merging without duplication and removing the "0" element
keys_set = union_several(keys_set);
keys_set = keys_set(keys_set ~= string(0));

Copy matrix rows matlab

Lets say i have a matrix A of 300x65. the last column(65th) contains ordered values (1,2,3). the first 102 elements are '1', the second 50 elements are '2' and the remainder will be '3'.
I have another matrix B, which is 3x65 and i want to copy the first row of B by the number of '1's in matrix A. The second row of B should be copied by the number of '2's in in matrix A and the 3th row should be copied by the remaining value of matrix A. By doing this, matrix B should result in a 300x65 matrix.
I've tried to use the repmat function of matlab with no succes, does anyone know how to do this?
There are many inconsistencies in your problem
first if you copy 1 row of B for every element of A(which will end up happening by your description) that will result in a matrix 19500x65
secondly copy its self is a vague term, do you mean duplicate? do you want to store the copied value into a new var?
what I gathered from your problem is you want to preform some operation between A and B to create a matrix and store it in B which in itself will cause the process to warp as it goes if you do not have another variable to store the result in
so i suggest using a third variable c to store the result in and then if you need it to be in b set b = C
also for whatever process you badly described I recommend learning to use a 'for' loop effectively because it seems like that is what you would need to use
syntax for 'for' loop
for i = [start:increment:end]
//loops for the length of [start:increment:end]
//sets i to the nth element of [start:increment:end] where n is the number of times the loop has run
end
If I understand your question, this should do it
index = A(:,end); % will be a column of numbers with values of 1, 2, or 3
newB = B(index,:); % B has 3 rows, which are copied as required by "index"
This should result in newB having the same number of rows as A and the same number of columns as the original B

I want to extract a row element in a matrix

X =
4 3
8 3
I want to extract the element in each row of X and do some operation on each of them separably (4,3) and (8,3). however the size of may be different based on some parameters in my code, so I want general formula to do such thing,
How I can use the for loop for solving this issue ?
This link shows how to extract specific lines (or columns) from a matrix http://www.mathworks.com/company/newsletters/articles/matrix-indexing-in-matlab.html
All you have to do is write a loop on an index ii to go through every line.
for ii=1:size(X,1)
a=myfun(X(ii,:));
end

Assigning the different row to another matrix after comparing two matrices

i have two matrices
r=10,000x2
q=10,000x2
i have to find out those rows of q which are one value or both values(as it is a two column matrix) different then r and allocate them in another matrix, right now i am trying this.i cannot use isequal because i want to know those rows
which are not equal this code gives me the individual elements not the complete rows different
can anyone help please
if r(:,:)~=q(:,:)
IN= find(registeredPts(:,:)~=q(:,:))
end
You can probably do this using ismember. Is this what you want? Here you get the values from q in rows that are different from r.
q=[1,2;3,4;5,6]
r=[1,2;3,5;5,6]
x = q(sum(ismember(q,r),2) < 2,:)
x =
3 4
What this do:
ismember creates an array with 1's in the positions where q == r, and 0 in the remaining positions. sum(.., 2) takes the column sum of each of these rows. If the sum is less than 2, that row is included in the new array.
Update
If the values might differ some due to floating point arithmetic, check out ismemberf from the file exchange. I haven't tested it myself, but it looks good.

Count the number of times a number is repeating in a vector

I have created a vector containing zeros and 1's using the following command in a for loop.
G(:,i)=rand(K,1)<rand;
Since this is part of a larger problem at a particular stage I need to count the number of 1's that are present in each column.
I have tried to find the count using a for loop which is very messy and takes too long.
I found that histc can be used for this but I get an error
histc(G(:,1),1)
First input must be non-sparse numeric array.
Is there a better way to do this or am I missing something here ?
If you have a matrix G containing zeroes and ones, and you want to know how many ones are in each column, all you need is SUM:
nZeroes = sum(G);
This will give you a vector containing a total for each column in G.