0

So, i'm a very beginner at Matlab and need some help in my task as i'm stuck here! Basically i have a lot of Matlab files which do the same functionality with different variables, i need to combine them in one Matlab file with one function and save these different values to iterate through them later and pass them to the function!

I've been searching which data type is suitable to hold the vars and i ended up with structs so my struct looks like:

W = struct('Band7', {7, 1099, 236, 260, 236, 260, 0}, 
           'Band2', {2, 1078, 236, 300, 236, 300, 0},
           'Band3', {3, 1829, 236, 100, 236, 100, 0},
           'Band4', {4, 1367, 206, 500, 206, 500, 0},
           'Band1', {1, 1123, 246, 170, 246, 170, 0}, ...);

My question is: how to loop through each band in the struct to pass it to the function like that -> RX_combined(W.Band4) and how to loop through each band's value inside the function itself?!

According to Wolfie's answer i update my code to:

function main 

% create a struct with the different vars
W = struct('Band7', {7, 1099, 236, 260, 236, 260, 0}, 
           'Band2', {2, 1078, 236, 300, 236, 300, 0},
           'Band3', {3, 1829, 236, 100, 236, 100, 0},
           'Band4', {4, 1367, 206, 500, 206, 500, 0},
           'Band1', {1, 1123, 246, 170, 246, 170, 0});

           fields = fieldnames(W)

% iterate over all bands and pass them to the function.
for i=1:numel(fields)
  fields(i)
  RX_combined(W.(fields{i}))
end 
end

my problem is how to access the values for every band inside the function?!


after some searching and working on the idea, i figured out that Matlab assumes that i'm distributing the cells of my array across the structure array elements rather than using every cell array as a unit which is what i wanted! referring to this answer .

To do that i fixed the problem by adding another curly braces to every cell array!

Now my code is:

function main 

% create a struct with the different values of the RX bands to merge the files in one!

W = struct('Band7',{{7, 1099, 236, 260, 236, 260, 0}},'Band2',{{2, 1078, 236, 300, 236, 300, 0}},'Band3',{{3, 1829, 236, 100, 236, 100, 0}},'Band4',{{4, 1367, 206, 500, 206, 500,0}},'Band1',{{4, 1367, 206, 500, 206, 500,0}});


fields = fieldnames(W);

% iterate over all the bands and pass them to the function.
for i=1:numel(fields)
  fields(i);
  %Wait for the User's keypress : this allows us to run every RX band file one by one
a = input('Run the new RX file (y/n)? ','s')
if strcmpi(a,'y')
  RX_combined( { W.(fields{i}) });
end 
end
end

function [] = RX_combined(band)

 P=int16([]);
numValues = numel(band);
for i = 1: numValues
    P.Band= band{i}{1}; 
    P.Channel_Frequency= band{i}{2}; 
    P.RD_GAIN_1= band{i}{3}; 
    P.RD_GAIN_ANA= band{i}{4};
    P.RX_GAIN_1= band{i}{5}; 
    P.RX_GAIN_ANA= band{i}{6}; 
    P.RX_ULP= band{i}{7}; 
end  
disp (P);
end    
Weloo
  • 625
  • 4
  • 16
  • You can get the field names of your struct like `f = fieldnames(W)` then loop through using `RX_combined(W.(f{ii}))`. That's using brackets around the field name because it's a string, where `ii` is the loop variable – Wolfie Oct 22 '17 at 09:39
  • @Wolfie Ok, so that's how i pass a certain band to the function, but what about looping through the band's values inside the function?! – Weloo Oct 22 '17 at 10:42
  • 2
    Do you want to do that within your `RX_combined` function or do you just want to pass one scalar value to that function? Either way you should use an array / 1D matrix with square brackets, not a cell array with curly braces, because your data is numerical. Then simply add another loop within the first (Or within the function) to loop over the array values – Wolfie Oct 22 '17 at 12:14
  • 1
    If this is representative of your data, you don't need a structure array at all; a two-dimensional array would be quicker and easier. But given the way you've organized your data, @Wolfie's suggestion of just changing from curly brackets `{}` to square brackets `[]` around your data will fix your problem. – beaker Oct 22 '17 at 15:07
  • I just wanted to be clear that i need struct because every band is a unit itself so when i iterate through it in the function 'RX_combined', i need to assign the values to 7 different variables! so if i can access it as in C like 'Band7.arg1= var1' ..etc – Weloo Oct 22 '17 at 17:08
  • Then you'll have to show your code for the function. I see no reason to define 7 distinct variables for array elements rather than accessing them as `array(1)`, `array(2)`, ..., `array(7)`. – beaker Oct 22 '17 at 18:42
  • @beaker exactly, i want to access the array with index rather defining the vars in the new function! – Weloo Oct 23 '17 at 04:37
  • Then use square brackets in your data to create an array rather than a cell array. And you don't have to put an exclamation mark after *every* sentence. It sounds like you're shouting. – beaker Oct 23 '17 at 14:53
  • @beaker it's just a habit :D i updated my code with the latest version of my idea. – Weloo Oct 24 '17 at 09:49
  • You're making this way more complicated than it has to be. Why do you think you need to loop over a 1x1 cell array in your function, and why are you using cell arrays to begin with? – beaker Oct 24 '17 at 15:04
  • You mean using numeric arrays instead of structs – Weloo Oct 26 '17 at 15:42

1 Answers1

1

Building off of the comments from Wolfie and beaker, below is two solutions: one using the cell array style originally proposed and another using a numeric array rather than a cell array (which I, like beaker, would recommend if you're expecting only numeric data as in your example).

Using cell array:

function [] = myFunction()

% create a struct with the different vars
W = struct('Band7', {7, 1099, 236, 260, 236, 260, 0},... 
           'Band2', {2, 1078, 236, 300, 236, 300, 0},...
           'Band3', {3, 1829, 236, 100, 236, 100, 0},...
           'Band4', {4, 1367, 206, 500, 206, 500, 0},...
           'Band1', {1, 1123, 246, 170, 246, 170, 0});

           fields = fieldnames(W);

% iterate over all bands and pass them to the function.

for i=1:numel(fields)
  disp(fields(i))
  %RX_combined(   W.(fields{i})  ); %Would return each value seperately. Only
                                    %first value will be passed to function, 
                                    %producing undesirable behaviour
  RX_combined( { W.(fields{i}) }); %curly braces make output cell array
end



end

function [] = RX_combined(band)
numValues = numel(band);
for i = 1: numValues
    disp(band{i}); %replace 'disp' with action you want to perform
end
end

Using numeric array: (note fewer curly braces and other weirdness)

function [] = myFunction()

% create a struct with the different vars
W = [7, 1099, 236, 260, 236, 260, 0;... 
     2, 1078, 236, 300, 236, 300, 0;...
     3, 1829, 236, 100, 236, 100, 0;...
     4, 1367, 206, 500, 206, 500, 0;...
     1, 1123, 246, 170, 246, 170, 0];

rowNames = {'Band7', 'Band2', 'Band3', 'Band4', 'Band1'};

% iterate over all bands(rows) and pass them to the function.
for i=1:size(W,1) %numel(fields)
  disp(rowNames{i})
  RX_combined( W(i,:) ); %passes ith row, all columns
end
end

function [] = RX_combined(band)
numValues = numel(band);
for i = 1:numValues
    disp(band(i)); %'band' is now numeric array, not cell array 
                   %so round braces instead of curly ones
end
end
JMikes
  • 572
  • 4
  • 12
  • Thanks for the answer, but i think i wasn't clear enough that every band is a unit itself so when i pass it to the function, i need to loop through and assign them to 7 variables in the function! – Weloo Oct 22 '17 at 17:02
  • Right. So to do that, you would replace the section of the code in RX_combined where I've written 'disp(band(i))', which simplify displays the value of the field, with code that assigns the variables in the band to the 7 variables that you have. To do that, you could use a 'switch' statement (see link below) to assign the value to the appropriate variable, using the loop variable 'i' as the switch expression. https://www.mathworks.com/help/matlab/ref/switch.html – JMikes Oct 23 '17 at 17:54
  • I updated my question with the final idea! thanks for the help! – Weloo Oct 24 '17 at 10:06