Mex matlab编码器:当矩阵应始终为二维时,不能转换被错误视为三维的矩阵
我有一个函数(下面给出了代码),我希望将其转换为MEX文件。我正在尝试使用matlab编码器来做到这一点Mex matlab编码器:当矩阵应始终为二维时,不能转换被错误视为三维的矩阵,mex,matlab-coder,Mex,Matlab Coder,我有一个函数(下面给出了代码),我希望将其转换为MEX文件。我正在尝试使用matlab编码器来做到这一点 %% Inputs dof = 3; num_divs = 72; ind_cr = 0 0 1 1 1 2 2 2 1 3 2 3 3 3 ind_switch = 1 1 1 0 1 0 0
%% Inputs
dof = 3;
num_divs = 72;
ind_cr =
0 0
1 1
1 2
2 2
1 3
2 3
3 3
ind_switch =
1
1
1
0
1
0
0
len_stat_atoms =
1
72
5184
72
373248
5184
72
num_stat_atoms =
108
111
111
3
111
3
3
coordFile =
[3x1 double]
[3x1 double]
[3x72x3 double]
[3x5184x3 double]
[3x373248x4 double]
radii_cell =
[108x1x3 double]
[111x72x3 double]
[111x5184x3 double]
[ 3x72x3 double]
[111x373248x4 double]
[ 3x5184x4 double]
[ 3x72x4 double]
stat_cell =
[3x1x108 double]
[3x72x111 double]
[3x5184x111 double]
[3x72x3 double]
[3x373248x111 double]
[3x5184x3 double]
[3x72x3 double]
%% Code that calls function
for i = 1:(dof*(dof+1)/2+1)
%% Load matrices
radii_mat = radii_cell{i,1};
stat_mat = stat_cell{i,1};
if ind_switch(i)
coordFile_mat = coordFile{ind_cr(i,2)+2};
end
%% Call the function
potential_mat = func_test(i,coordFile_mat,radii_mat,stat_mat,...
ind_cr,len_stat_atoms,num_stat_atoms,num_coord_atoms,...
counter,num_divs,dof);
end
%% Function code
function potential_mat = func_test(i,coordFile_mat,radii_mat,stat_mat,...
ind_cr,len_stat_atoms,num_stat_atoms,num_coord_atoms,...
counter,num_divs,dof);
potential_mat = zeros(num_coord_atoms,num_divs^dof);
for j = 1:size(coordFile_mat,3)
%% Compute distances
a = zeros(3,len_stat_atoms(i));
a = coordFile_mat(:,1:len_stat_atoms(i),j);
b = zeros(3,len_stat_atoms(i),num_stat_atoms(i));
b = repmat(a,[1 1 num_stat_atoms(i)]);
c = zeros(1,len_stat_atoms(i),num_stat_atoms(i));
c = sqrt(sum((b - stat_mat).^2,1));
d = zeros(len_stat_atoms(i),num_stat_atoms(i));
d = shiftdim(c,1);
distances = zeros(num_stat_atoms(i),len_stat_atoms(i));
distances = d';
%% Compute clashes and potentials
clashes = distances < radii_mat(:,:,j);
potentials = zeros(size(distances));
potentials(clashes) = (1-(distances(clashes)./radii_mat(find(clashes)+numel(clashes)*(j-1))).^6).^2;
%% Iterate over nodes
col = ind_cr(i,1); row = ind_cr(i,2);
if col == 1
ind_kron = repmat(1:size(potentials,2),[num_divs^(dof-row) 1]);
potentials = potentials(:,ind_kron(:)');
elseif row == dof
vec_repmat = [1 num_divs^(col-1)];
potentials = repmat(potentials,vec_repmat);
elseif col > 0
vec_repmat = [1 num_divs^(col-1)];
ind_kron = repmat(1:size(potentials,2),[num_divs^(dof-row) 1]);
potentials = repmat(potentials(:,ind_kron(:)'),vec_repmat);
else
potentials = repmat(sum(potentials),[1 num_divs^dof]);
end
counter = counter+1;
potential_mat(counter,:) = sum(potentials,1);
end
end
Matlab编码器确定
c
的大小为1 x:?x:?
,这是正确的。然后,d=shiftim(c,1)
行应生成大小为:?x:?
,然后我将其转置。但是,它无法正确移动d
的维度,并将其大小设置为:?x:?x:?
。这将导致转置错误。我如何解决这个问题?此外,出于我自己的启发,为什么matlab coder不能正确分配变量的维度,特别是a
,b
,c
,d
,和距离
?文档将其描述为(d
是在循环中创建的,因此似乎是可变大小):
对于可变大小的N-D阵列,size函数在生成的代码中返回的结果可能与在MATLAB中返回的结果不同在生成的代码中,size(A)返回一个固定长度的输出,因为它不会删除可变大小N-D数组的尾随单例维度。相比之下,MATLAB中的size(A)返回一个可变长度的输出,因为它会删除后面的单个维度
例如,如果数组A
的形状是:?x:?x:?
和大小(A,3)=1
,大小(A)
返回:
- 生成代码中的三元向量
- MATLAB代码中的二元向量
size
功能的使用有关。然而,在您的情况下,您只希望能够转置。解决方法是使用permute
,因为转置是permute
的一般情况:
% after shiftdim:
distances = permute(d,[2 1 3]) % same as d' for 2d array, but handles 3d
您也可以将shiftim
完全剪掉:
distances = permute(c,[2 3 1])
另外,我对Coder没有太多经验,但它真的需要所有那些使用
零的初始化吗?它们似乎没有必要
distances = permute(c,[2 3 1])