您的循环有一个主要问题:您将所有条件嵌套在彼此之下,因此仅当第一个条件为false 时才检查i+1 和i+2,但是当您到达时再次检查它们循环的下一次迭代。如果Dataset{272,1}(i+1,3) == -2,那么您已经知道在下一次迭代中(当您将Dataset{272,1}(i,3) 与-3 进行比较时)它将返回false,但它是false 还是true?!根据你的循环,这取决于你问这个的何时......
这里有两个选项可以纠正这个问题,仍然使用循环。它循环所有k 的第一种方式(我将i 替换为k 以不覆盖MATLAB 中的虚数单位),但将Dataset{272,1}(i+1,3) 与不同的数字进行比较:
c = [-1 -3 -2];
for k = 1:length(Dataset)
if Dataset{272,1}(k,3) ~= c(mod(k,3)+1);
eraseidx = Dataset{272,1}(k,3);
end
end
另一种选择是比较三元组中的数据:
for k = 1:3:length(Dataset)
if Dataset{272,1}(k,3) ~= -3
eraseidx = Dataset{272,1}(k,3);
end
if Dataset{272,1}(k+1,3) ~= -2
eraseidx = Dataset{272,1}(k+1,3);
end
if Dataset{272,1}(k+2,3) ~= -1
eraseidx = Dataset{272,1}(k+2,3);
end
end
现在你只将有问题的记录保存到eraseidx,但每次满足任何条件时都会覆盖它,所以你还需要索引eraseidx:
eraseidx = zeros(length(Dataset),1);
c = [-1 -3 -2];
for k = 1:length(Dataset)
if Dataset{272,1}(k,3) ~= c(mod(k,3)+1);
eraseidx(k) = Dataset{272,1}(k,3);
end
end
但是,如果您只想删除这些记录,您可以将 k 单独保存为逻辑索引,而不是所有记录。另外,在我看来,您的循环应该在1:length(Dataset{272,1}) 上运行,所以:
eraseidx = false(length(Dataset{272,1}),1);
c = [-1 -3 -2];
for k = 1:length(Dataset{272,1})
eraseidx(k) = Dataset{272,1}(k,3) ~= c(mod(k,3)+1);
end
这可以很容易地向量化为:
c = [-1 -3 -2];
k = 1:length(Dataset{272,1});
eraseidx = Dataset{272,1}(k,3) ~= c(mod(k,3)+1).';
所以现在eraseidx 将是一个逻辑向量,因此Dataset{272,1}(eraseidx,:) 将是Dataset{272,1} 中要删除的所有记录。 编辑:要删除它们,您只需写:Dataset{272,1}(eraseidx,:) = []。
矢量化所有Dataset
如果所有单元格中的所有数据都具有相同的大小和形状,您可以使用cell2mat将其转换为ND数组,然后对所有数据进行一次向量化操作:
data = reshape(cell2mat(Dataset.'),[],3,numel(Dataset)); % convert to 3D array
c = [-1 -3 -2];
k = 1:size(data,1);
correct = c(mod(k,3)+1).'; % the correct values to compare
eraseidx = squeeze(bsxfun(@ne,data(:,3,:),correct));
现在eraseidx 中的每一列对应Dataset 中的第三列,因此Dataset(k,1) 的结果在eraseidx(:,1) 中给出。
要删除 eraseidx 中的所有 true 记录,您可以使用简单的循环:
for k = 1:numel(Dataset)
Dataset{k}(eraseidx(:,k),:) = [];
end
请注意,您不能直接从data 中删除记录,因为数组在第三维的每个元素中不能有不同的行数。
如果Dataset 必须是一个元胞数组...
如果您使用单元格将数据保留在Dataset 中,因为它的大小和形状不同,您可以针对所有过程调整上述循环:
c = [-1 -3 -2];
for k = 1:numel(Dataset)
eraseidx = Dataset{k,1}(:,3) ~= c(mod(1:length(Dataset{k,1}),3)+1).';
Dataset{k,1}(eraseidx,:) = [];
end
或者你可以使用cellfun(基本上是一个紧凑的循环):
c = [-1 -3 -2];
delfun = @(M) M(M(:,3)==c(mod(1:length(M),3)+1).',:);
Dataset_fixed = cellfun(delfun,Dataset,'UniformOutput',false);
delfun 是一个匿名函数,它只从Dataset 中的每个单元格中检索想要的记录。现在 Dataset_fixed 是 Dataset 没有删除的行。