Matlab:循环中的条件绘图可以矢量化吗?
我想做垂直线的有条件绘图,根据整型向量的值改变颜色。这些值是范围为0-4的整数 目前,我正在使用循环遍历表格以绘制线条。这是可行的,但对于大量数据来说,这需要时间,我想知道它是否可以矢量化 附件是一个精简版本的脚本,用于循环数据向量(示例),该脚本简单地循环向量,并基于整数的值绘制垂直线 我还将在下面附加我创建的名为“SAMPLE”的简单变量,以粘贴到您的工作区中Matlab:循环中的条件绘图可以矢量化吗?,matlab,plot,vectorization,Matlab,Plot,Vectorization,我想做垂直线的有条件绘图,根据整型向量的值改变颜色。这些值是范围为0-4的整数 目前,我正在使用循环遍历表格以绘制线条。这是可行的,但对于大量数据来说,这需要时间,我想知道它是否可以矢量化 附件是一个精简版本的脚本,用于循环数据向量(示例),该脚本简单地循环向量,并基于整数的值绘制垂直线 我还将在下面附加我创建的名为“SAMPLE”的简单变量,以粘贴到您的工作区中 for i=1:size(sample,1) if sample(i)==1 line( [i
for i=1:size(sample,1)
if sample(i)==1
line( [i i] ,[0 10], 'Marker','.','LineStyle','-','Color','r');
elseif sample(i)==2
line( [i i] ,[0 10], 'Marker','.','LineStyle','-','Color','b');
elseif sample(i)==3
line( [i i] ,[0 10], 'Marker','.','LineStyle','-','Color',[1 .5 0]);
elseif sample(i)==4
line( [i i] ,[0 10], 'Marker','.','LineStyle','-','Color','g');
end
end
变量:
sample=[[3;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;1;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;2;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;3;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;0;0;0;0]];
但是,是否有可能以这种方式“矢量化”绘图,而不必像我所做的那样在循环中迭代进行
我想换成这样:
colors=[1 0 0,
0 1 0,
1 0.5 0,
0 0 1];
nnsamples=samples(samples~=0);
for ii=1:size(nnsamples,1)
line( [ii ii] ,[0 10], 'Marker','.','LineStyle','-','Color',colors(nnsamples(ii),:));
end
利用绘制直线时,MATLAB将跳过值为
NaN
的点这一事实
% Your vector
sample=[3;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;1;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;2;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;3;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;0;4;0;0;0;0];
% Your colors
colors = [
1 0 0
0 0 1
1 .5 0
0 1 0];
for idx = 1:4
% Find the index of each of your integers
X = find(sample == (idx));
% Force X to be a row vector
X = X(:)';
% Stack two X's on top of one another with a third row filled
% with NaNs. Fill in your Y values in the same way while
% you're at it.
Y = [zeros(size(X)); 10 + zeros(size(X)); nan(size(X))];
X = [X; X; nan(size(X))]; %#ok<AGROW>
% Matlab is column major. By using the colon here, you
% produce a vector that is [X1 X1 nan X2 X2 nan ... etc.]
X = X(:);
Y = Y(:);
% Draw the line
line(X, Y, 'Marker', '.', 'LineStyle', '-', 'Color', colors(idx, :))
end
使用
timeit
进行基准测试时,我的机器上的基准测试时间为0.0065706秒,而操作码基准测试时间为1.4861秒。谢谢,我会将这些更改添加到我当前的脚本中,因为这是我所做工作的更紧凑的形式。但我仍然在想,是否有可能以某种方式删除所有循环,以提高处理该循环的效率?例如,在170K值上进行测试时,两种类型的处理时间都刚刚超过3秒。170K绘图时间为3秒?这很快@pelty你的解决方案平均来说稍微快一点。下面是它们的区别。你可以看到原件和你的,以及底部的平均值。连同每次计算的大致时间,运行它5次。是的,您编辑的版本甚至比原始版本稍快。您可以查看原始版本、原始版本和编辑版本的时间。哇!这绝对是更有效的,并且符合我所期待的。使用我之前使用的基准测试,运行它大约需要3秒钟。使用相同的数据与这个模型,它花了0.007036秒。因此,速度提高了约400倍。:)
sample = zeros(1, 1e6);
for idx = 1:4
sample(randi(1e6, 1, 1000)) = idx;
end