How to get all possible combinations of data in a cell?

3 Ansichten (letzte 30 Tage)
Jethro G
Jethro G am 10 Feb. 2017
Kommentiert: José-Luis am 10 Feb. 2017
I have a cell with 4 rows that contains a number of data in this format:
A, B, C, D
E, F,
1, 2, 3, 4
5, 6, 7
How can i get all possible combinations (one from each row)? For example AE15, AF15, and so on..
  2 Kommentare
José-Luis
José-Luis am 10 Feb. 2017
Bearbeitet: José-Luis am 10 Feb. 2017
What have you tried so far? This looks like a homework question.
Hints: The ugly solution would involve nested loops. A bit better would be to look into ndgrid(). bsxfun() could probably be used. Etc...
Jethro G
Jethro G am 10 Feb. 2017
Hah I wish I was still at the age where I had homework to do. I don't have an issue with looping everything for each row manually i can do that. The problem is that I'm trying to find a method that executes the required number of loops irregardless of the size of cell that the user provides.
IE whether the user gives a cell with 10 rows or 3 rows

Melden Sie sich an, um zu kommentieren.

Antworten (1)

José-Luis
José-Luis am 10 Feb. 2017
Bearbeitet: José-Luis am 10 Feb. 2017
data = {{'A', 'B', 'C', 'D'}; ...
{'E','F',};...
{1, 2, 3, 4};...
{5, 6, 7}};
cell_size = cellfun(@(x) size(x,2) ,data);
tot_elements = cell_size' * cell_size;
[I,J,K,L] = ind2sub(cell_size',1:tot_elements);
result = [cell2mat(data{1}(I)'), cell2mat(data{2}(J)'), char([data{3}{K}]+48)', char([data{4}{L}]+48)'];
EDIT Going out of my way to avoid loops and having it work for variable-size input:
data = {{'A', 'B', 'C', 'D'}; ...
{'E','F',};...
{1, 2, 3, 4};...
{5, 6, 7}};
cell_size = cellfun(@(x) size(x,2) ,data);
tot_elements = prod(cell_size);
%Turning data into a cell array of character array
is_a_number = cellfun(@(x) isnumeric(cell2mat(x)),data);
data(is_a_number) = cellfun(@(x) {char(cell2mat(x) + 48)},data(is_a_number));
data(~is_a_number) = cellfun(@(x) {cell2mat(x)},data(~is_a_number));
%Avoiding ind2sub, convoluted way of obtaining the indexes
idx = (1:numel(data));
idx_array = bsxfun(@(x,y) ceil( (mod(x-1,prod(cell_size(1:y)))+1) ./ ...
(prod(cell_size(1:y)) / cell_size(y) ) ),...
(1:tot_elements)', idx);
%Finally getting the results based on idx_array
result = cell2mat(cellfun(@(x) {data{x}(idx_array(:,x))}, num2cell(idx))')';
Not an (explicit) loop in sight but not pretty. Not very maintainable either. I won't directly understand this if I look at it down the line. Loops in this case would be clearer, IMO.
  4 Kommentare
Jethro G
Jethro G am 10 Feb. 2017
Bearbeitet: Jethro G am 10 Feb. 2017
Thank you very much. I guess the only thing that's left for me now is instead of defining IJKL (which only works for 4-row cells), to generete those depending on the number of rows in the cell that the user provides, but i'm sure i can figure that out! Thanks a lot!
José-Luis
José-Luis am 10 Feb. 2017
My pleasure. Updated for variable input size.

Melden Sie sich an, um zu kommentieren.

Kategorien

Mehr zu Resizing and Reshaping Matrices finden Sie in Help Center und File Exchange

Produkte

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by