Updating one field in every element of a Matlab struct array

Carl picture Carl · Feb 16, 2012 · Viewed 11.8k times · Source

Suppose I have a struct array arr, where each element has a bunch of fields, including one called val. I'd like to increment each element's val field by some constant amount, like so:

for i = 1:length(arr)
    arr(i).val = arr(i).val + 3;
end

This obviously works, but I feel there should be a way to do this in just one line of code (and no for loop). The best I've come up with is two lines and requires a temp variable:

newVals = num2cell([arr.val] + 3);
[arr.val] = deal(newVals{:});

Any ideas? Thanks.

Answer

mathematical.coffee picture mathematical.coffee · Feb 16, 2012

Just a note, the deal isn't necessary there:

[arr.val] = newVals{:}; % achieves the same as deal(newVals{:})

The only other way I know how to do this (without the foor loop) is using arrayfun to iterate over each struct in the array:

% make a struct array
arr = [ struct('val',0,'id',1), struct('val',0,'id',2), struct('val',0,'id',3) ]

% some attempts
[arr.val]=arr.val; % fine
[arr.val]=arr.val+3; % NOT fine :(

% works !
arr2 = arrayfun(@(s) setfield(s,'val',s.val+3),arr)

That last command loops over each struct in arr and returns a new one where s.val has been set to s.val=3.

I think this is actually less efficient than your previous two-liner and the for loop though, because it returns a copy of arr as opposed to operating in-place.

(It's a shame Matlab doesn't support layered indexing like [arr.val]=num2cell([arr.val]+3){:}).