我有一个非固定的维矩阵M,我想从中访问单个元素。 元素的索引包含在向量J中。
例如:
M = rand(6,4,8,2);
J = [5 2 7 1];
output = M(5,2,7,1)
这次M有4个维度,但事先并不知道。这取决于我正在编写的算法的设置。它也可能是那个
M = rand(6,4);
J = [3 1];
output = M(3,1)
所以我不能简单地使用
output=M(J(1),J(2))
我在考虑使用sub2ind,但这也需要将变量逗号分开..
@gnovice
这有效,但我打算在矩阵M
中使用这种元素提取相当多。因此,如果每次访问cellJ
时都必须创建一个临时变量M
,这不会极大地减慢计算速度吗?
我也可以写一个单独的函数
function x= getM(M,J)
x=M(J(1),J(2));
% M doesn't change in this function, so no mem copy needed = passed by reference
end
并根据算法的不同配置进行调整。这当然是速度与灵活性的考虑因素,我没有将其纳入我的问题中。
但是:这只能用于获取元素,设置除了实际使用索引之外别无他法(最好是线性索引)。我仍然认为sub2ind是一个选项。我想要的最终结果是:
function idx = getLinearIdx(J, size_M)
idx = ...
end
function lin_idx = Lidx_ml( J, M )%#eml
%LIDX_ML converts an array of indices J for a multidimensional array M to
%linear indices, directly useable on M
%
% INPUT
% J NxP matrix containing P sets of N indices
% M A example matrix, with same size as on which the indices in J
% will be applicable.
%
% OUTPUT
% lin_idx Px1 array of linear indices
%
% method 1
%lin_idx = zeros(size(J,2),1);
%for ii = 1:size(J,2)
% cellJ = num2cell(J(:,ii));
% lin_idx(ii) = sub2ind(size(M),cellJ{:});
%end
% method 2
sizeM = size(M);
J(2:end,:) = J(2:end,:)-1;
lin_idx = cumprod([1 sizeM(1:end-1)])*J;
end
方法2是20(少量索引集(=P
)要转换)到80(大量索引集(=P
))比方法1快一点。容易选择
答案 0 :(得分:12)
对于J
可以是任意长度的一般情况(我假设它总是与M
中的维数相匹配),您有几个选项:
您可以使用NUM2CELL函数将J
的每个条目放在单元格数组的单元格中,然后使用{{3}从此单元格数组创建comma-separated list }}:
cellJ = num2cell(J);
output = M(cellJ{:});
您可以回避colon operator函数,并通过一些数学计算自己SUB2IND:
sizeM = size(M);
index = cumprod([1 sizeM(1:end-1)]) * (J(:) - [0; ones(numel(J)-1, 1)]);
output = M(index);
答案 1 :(得分:0)
这是gnovices选项2)的一个版本,它允许处理整个下标矩阵,其中每行包含一个下标。例如,3个下标:
J = [5 2 7 1
1 5 2 7
4 3 9 2];
sizeM = size(M);
idx = cumprod([1 sizeX(1:end-1)])*(J - [zeros(size(J,1),1) ones(size(J,1),size(J,2)-1)]).';