Assign a Sub Array to Array Knowing the Number of Dimensions at Run Time

Assume we have tA and tB with the same number of dimesions. We also have all(size(tB) <= size(tA)) == true.
The task is to embed tB in tA. Something like: tA(1:size(tB, 1), 1:size(tB, 2), ..., 1:size(tB, n)) = tB. Yet since we know the number of dimensions only at runtime, it can't be written explicitly like that.
The question, is there an efficient way to do so without eval or explicitly computer the cartesian product and use sub2ind()?

 Accepted Answer

OK, It turns out it can be done using Cell Arrays:
vSizeB = size(tB);
numDims = length(vSizeB); %<! Equals to ndims(tB)
cIdx = cell(numDims, 1);
for ii = 1:numDims
cIdx{ii} = 1:vSizeB(ii);
end
tA(cIDx{:}) = tB;

6 Comments

Hiding the loop:
tmp = arrayfun(@(n)1:n,size(tB),'uni',0)
tA(tmp{:}) = tB;
Why not this?
cIdx = cell(1,ndims(tB));
for ii = 1:ndims(tB)
cIdx{ii} = 1:size(tB,ii);
end
tA(cIDx{:}) = tB;
This is essentially what I suggested in my answer.
@Stephen, Your code won't work as you need the 1:vSizeB(ii) vector and not only a single number. @Rik, What's the difference from my answer?
  1. Direct calls to size instead of creating a new vector and having to index it
  2. No calls to length (you never need it, as you prove in your comment already)
  3. More compact
So no major differences. Just like your answer has no major differences from my answer.
"Your code won't work as you need the 1:vSizeB(ii) vector and not only a single number"
Lets try it:
tA = nan(5,4,3);
tB = randi(9,4,3,2);
tmp = arrayfun(@(n)1:n,size(tB),'uni',0);
tA(tmp{:}) = tB
tA =
tA(:,:,1) = 4 9 5 NaN 2 1 5 NaN 2 2 2 NaN 7 5 4 NaN NaN NaN NaN NaN tA(:,:,2) = 6 1 8 NaN 9 4 5 NaN 5 4 4 NaN 4 3 3 NaN NaN NaN NaN NaN tA(:,:,3) = NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN NaN
@Stephen, Well you edited the comment. It was, at first, only num2cell().

Sign in to comment.

More Answers (1)

There is probably a better way, but you can fill a cell array with the index vectors (simple loop with ndims), and then use this:
tA(inds{:}) = tB;

Products

Community Treasure Hunt

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

Start Hunting!