细胞阵列的操作
Manipulation of cell arrays
我有两个大小为 [1X5] 的元胞数组
K= {} {O1,O2,O3,O4} {O1,O3} {O1,O2,O3,O4} {O1,O2,O3,O4}
W= {O3}{O2}{O2,O3}{O2,O4}{O4}
我想得到一个名为 S
的元胞数组,大小为 [1X4],如下所示:
我将 K{i}
的内容放在每个 S{j}
中,其中 j
是 W{i}
内容的索引(例如单元格 W{3}
的内容为 O2
和 O3
,所以 j=2,3
。我将 K{3}
的内容放在单元格 S{2}
和 S{3}
中)。
之后我在每个 S{i}
中添加一个内容 Oi
并且我在 S
中删除冗余。
预期结果如下:
S={O1}{O1,O2,O3,O4}{O1,O3}{O1,O2,O3,O4}
您可以为此使用 union
函数以及多个循环:
function S = q47140074(K,W)
if nargin < 2
% Input data:
K = {"", ("O"+(1:4).').', ("O"+[1;3]).', ("O"+(1:4).').', ("O"+(1:4).').'};
W = {"O3", "O2", ("O"+(2:3).').', ("O"+[2;4]).', "O4"};
end
% Preprocess data:
Wn = cellfun(@stripO,W,'UniformOutput',false);
% Preallocation:
S = num2cell(strings(1, max(cellfun(@max,Wn))));
% Computation:
for ind1 = 1:numel(Wn)
tmpW = Wn{ind1};
for ind2 = 1:numel(tmpW)
S{tmpW(ind2)} = union(S{tmpW(ind2)}, K{tmpW(ind2)});
end
end
for ind1 = 1:numel(S)
S{ind1} = setdiff(union(S{ind1},"O" + ind1),"");
end
end
function out = stripO(in)
out = str2double(strip(in,'left','O'));
end
结果:
这是一个使用 accumarray and unique 的解决方案:
K= {{} ,{'O1','O2','O3','O4'} ,{'O1','O3'} ,{'O1','O2','O3','O4'} ,{'O1','O2','O3','O4'}};
W= {{'O3'},{'O2'},{'O2','O3'},{'O2','O4'},{'O4'}};
subs = sscanf(cell2mat([W{:}]),'O%d');
m = max(subs);
subs = [subs;(1:m).'];
vals = repelem(1:numel(W),cellfun(@numel,W));
vals = [vals numel(K)+1:numel(K)+m]
K = [K num2cell(cellstr(num2str((1:m).','O%d'))).'];
%If your data are string scalars use the following K
%K = [K num2cell(string(cellstr(num2str((1:m).','O%d')))).']
result = accumarray(subs,vals,[],@(x){unique([K{x}])})
result =
{
[1,1] =
{
[1,1] = O1
}
[2,1] =
{
[1,1] = O1
[1,2] = O2
[1,3] = O3
[1,4] = O4
}
[3,1] =
{
[1,1] = O1
[1,2] = O3
}
[4,1] =
{
[1,1] = O1
[1,2] = O2
[1,3] = O3
[1,4] = O4
}
}
我有两个大小为 [1X5] 的元胞数组
K= {} {O1,O2,O3,O4} {O1,O3} {O1,O2,O3,O4} {O1,O2,O3,O4}
W= {O3}{O2}{O2,O3}{O2,O4}{O4}
我想得到一个名为 S
的元胞数组,大小为 [1X4],如下所示:
我将 K{i}
的内容放在每个 S{j}
中,其中 j
是 W{i}
内容的索引(例如单元格 W{3}
的内容为 O2
和 O3
,所以 j=2,3
。我将 K{3}
的内容放在单元格 S{2}
和 S{3}
中)。
之后我在每个 S{i}
中添加一个内容 Oi
并且我在 S
中删除冗余。
预期结果如下:
S={O1}{O1,O2,O3,O4}{O1,O3}{O1,O2,O3,O4}
您可以为此使用 union
函数以及多个循环:
function S = q47140074(K,W)
if nargin < 2
% Input data:
K = {"", ("O"+(1:4).').', ("O"+[1;3]).', ("O"+(1:4).').', ("O"+(1:4).').'};
W = {"O3", "O2", ("O"+(2:3).').', ("O"+[2;4]).', "O4"};
end
% Preprocess data:
Wn = cellfun(@stripO,W,'UniformOutput',false);
% Preallocation:
S = num2cell(strings(1, max(cellfun(@max,Wn))));
% Computation:
for ind1 = 1:numel(Wn)
tmpW = Wn{ind1};
for ind2 = 1:numel(tmpW)
S{tmpW(ind2)} = union(S{tmpW(ind2)}, K{tmpW(ind2)});
end
end
for ind1 = 1:numel(S)
S{ind1} = setdiff(union(S{ind1},"O" + ind1),"");
end
end
function out = stripO(in)
out = str2double(strip(in,'left','O'));
end
结果:
这是一个使用 accumarray and unique 的解决方案:
K= {{} ,{'O1','O2','O3','O4'} ,{'O1','O3'} ,{'O1','O2','O3','O4'} ,{'O1','O2','O3','O4'}};
W= {{'O3'},{'O2'},{'O2','O3'},{'O2','O4'},{'O4'}};
subs = sscanf(cell2mat([W{:}]),'O%d');
m = max(subs);
subs = [subs;(1:m).'];
vals = repelem(1:numel(W),cellfun(@numel,W));
vals = [vals numel(K)+1:numel(K)+m]
K = [K num2cell(cellstr(num2str((1:m).','O%d'))).'];
%If your data are string scalars use the following K
%K = [K num2cell(string(cellstr(num2str((1:m).','O%d')))).']
result = accumarray(subs,vals,[],@(x){unique([K{x}])})
result =
{
[1,1] =
{
[1,1] = O1
}
[2,1] =
{
[1,1] = O1
[1,2] = O2
[1,3] = O3
[1,4] = O4
}
[3,1] =
{
[1,1] = O1
[1,2] = O3
}
[4,1] =
{
[1,1] = O1
[1,2] = O2
[1,3] = O3
[1,4] = O4
}
}