Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/matlab/18.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/ansible/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Arrays 从一点开始的矩阵上的螺旋环_Arrays_Matlab_Loops_Matrix - Fatal编程技术网

Arrays 从一点开始的矩阵上的螺旋环

Arrays 从一点开始的矩阵上的螺旋环,arrays,matlab,loops,matrix,Arrays,Matlab,Loops,Matrix,我有一个二维网格,如下所示,希望从X,Y开始,保存窗口的角(W)和重叠(OP)。我试过代码,但没有一个适合我的目的 正如所演示的,我想从一个随机点(黑色单元格)开始,将每个新窗口的角点位置(以黑色圆圈显示)保存在一个螺旋循环中。该算法应用于任何网格大小(不一定为正方形)和任何起点位置 Matlab还有一个类似于我想要的函数(螺旋),但它不需要网格、窗口大小和重叠(OP) 我希望这个数字的输出如下:(8,12) (11,12) (11,9) (8,9) (4,9) (4,12) (4,15) 我

我有一个二维网格,如下所示,希望从X,Y开始,保存窗口的角(W)和重叠(OP)。我试过代码,但没有一个适合我的目的

正如所演示的,我想从一个随机点(黑色单元格)开始,将每个新窗口的角点位置(以黑色圆圈显示)保存在一个螺旋循环中。该算法应用于任何网格大小(不一定为正方形)和任何起点位置

Matlab还有一个类似于我想要的函数(螺旋),但它不需要网格、窗口大小和重叠(OP)

我希望这个数字的输出如下:(8,12) (11,12) (11,9) (8,9) (4,9) (4,12) (4,15)

我使用以下代码,从一个角开始,使用定义的W、OP和矩阵大小逐步填充矩阵:

W = [10 12];
OP = [4 3];

M = zeros(100,110);

for i=[1:W(1)-OP(1):size(M,1)-W(1), size(M,1)-W(1)+1]
  for j=[1:W(2)-OP(2):size(M,2)-W(2), size(M,2)-W(2)+1]
      block = rand(W(1),W(2));
      M(i:i+W(1)-1, j:j+W(2)-1) = block;
      imagesc(M); axis equal tight xy
      pause(.1)
  end;
end;
因此,更清楚地说,我应该如何更改“上述”代码,以便从一个位置(x,y)开始,并根据W,OP和size(M)螺旋填充整个矩阵


谢谢

下面是一段代码,它产生了预期的输出。在这些情况下,仅需对螺旋槽进行细微更改即可满足您的要求:

function demo()
spiral_generic([10,11],[3,4])
W = [10 12];
OP = [4 3];
%make sure your start point is really on the grid of r and c, this is not checked!
start = [19,28];
M = zeros(100,110);
r=[1:W(1)-OP(1):size(M,1)-W(1), size(M,1)-W(1)+1];
c=[1:W(2)-OP(2):size(M,2)-W(2), size(M,2)-W(2)+1];
startindex=[find(r==start(1),1,'first'),find(c==start(2),1,'first')];
A=spiral_generic([numel(r),numel(c)],startindex);
[~,idx]=sort(A(:));
[ridx,cidx]=ind2sub(size(A),idx);
%blocks contains the lower left corners in order of processing.
blocks=[r(ridx);c(cidx)];
for blockindex=blocks
       block = rand(W(1),W(2));
       M(blockindex(1):blockindex(1)+W(1)-1, blockindex(2):blockindex(2)+W(2)-1) = block;
       imagesc(M);
       pause(.1)
end

end
function A = spiral_generic(n, P)
% Makes NxN matrix filled up spirally starting with point P
  r = max([P - 1, n - P]);              % Radius of the bigger matrix
  M = spiral(2 * r + 1);                % Bigger matrix itself
  M = permute(M,[2,1]);                 % changing start direction of the spiral
  M = M(:,end:-1:1);                    % chaning spin orientation
  C = r + 1 - (P - 1);                  % Top-left corner of A in M
  A = M(C(1):C(1)+n(1)-1, C(2):C(2)+n(2)-1);  % Get the submatrix
  [~, order] = sort(A(:));              % Get elements' order
  A(order) = 1:(n(1)*n(2));                     % Fill with continous values
end
基本问题 将数据定义为:

step = 3;  %// step size
x0 = 8;    %// x coordinate of origin
y0 = 12;   %// y coordinate of origin
N = 32;    %// number of steps
然后,螺旋线的坐标可作为复平面中的值获得,如下†:

当然,x和y坐标是

x = real(z);
y = imag(z);
对于上面给出的示例值,
plot(z,'o-)
(或
plot(x,y,'o-)
)生成图形

†关键是生成序列
1,2,3,3,4,4,5,5,6,6,7,7,7,8,8,8…
。序列是4n+1的平方根的整数部分,对于n=1,2,3

如何包括重叠和窗口大小 要考虑重叠,请从
步骤
中减去其值

<> >考虑窗口大小,<代码> N< /代码>应足够大,使螺旋到达窗口边界的某个点;然后只保留前面的几点

由于很难预先计算出
N
应该有多大,一种可能的方法是在循环中以指数形式增加
N
,直到它足够大。指数增长确保了循环迭代的数量将很小。下面的代码使用2的幂表示
N

%// Data
step = 3;     %// step size
overlap = 1;  %// overlap
x0 = 20;      %// x coordinate of origin
y0 = 15;      %// y coordinate of origin
xmin = 0;     %// window boundary: min x
xmax = 40;    %// window boundary: max x
ymax = 30;    %// window boundary: min y
ymin = 0;     %// window boundary: max y

%// Computations
stepov = step-overlap;
N = 8; %// Initial value. Will be increased as needed
done = false;
while ~done
    z = x0+1j*y0 + stepov*cumsum([0 -1j.^(-floor(sqrt(4*(0:N)+1))-1)]);
        %// compute coordinates of N points
    ind = find(real(z)<xmin | real(z)>xmax | imag(z)<ymin | imag(z)>ymax, 1);
        %// find index of first z out of boundary, if any
    done = ~isempty(ind); %// exit if we have reached outside window boundary
    N = N*2; %// increase number of steps for next try
end
z = z(1:ind-1); %// only keep values that are within the boundary
x = real(z);
y = imag(z);
%//数据
步骤=3;%//步长
重叠=1;%//重叠
x0=20;%//x原点坐标
y0=15;%//原点y坐标
xmin=0;%//窗口边界:最小x
xmax=40;%//窗口边界:最大x
ymax=30;%//窗口边界:最小y
ymin=0;%//窗口边界:最大y
%//计算
stepov=阶跃重叠;
N=8;%//初始值。将根据需要增加
完成=错误;
完成时
z=x0+1j*y0+stepov*cumsum([0-1j.^(-floor(sqrt(4*(0:N)+1))-1)];
%//计算N个点的坐标
ind=find(实(z)xmax | imag(z)ymax,1);
%//查找边界外第一个z的索引(如果有)
完成=~isempty(ind);%//如果我们到达窗口边界外,请退出
N=N*2;%//增加下一次尝试的步骤数
结束
z=z(1:ind-1);%//仅保留边界内的值
x=实(z);
y=imag(z);
根据代码中指示的数据,获得的图形如下所示。请注意,最后一点是(38,0)。下一个点是(38,-2),它位于窗口边界之外


这个数字很不清楚。我不能告诉您要保存哪些位置。您能使用最少的样本输入数据并告诉我们预期的输出吗?而且,重叠区域可能不止一个元素宽,对吗?我编辑了这个问题。是的,OP可以是多个元素。我在文档中没有看到任何
spiral
函数。你有参考资料吗?@Sam:我想你的例子应该是
(8,12)(11,12)(11,9)(8,9)(5,9)(5,12)(5,15)
,所以步骤总是3?它对平方矩阵有效吗?我的矩阵不是正方形,它的大小是101x200,我的窗口大小不是正方形,它是20x15,重叠是5@Sam:已更新,所需的微小更改。我可以定义起点吗?(“代码中的中心”),因为我的起点不在矩阵的中心。如果你看上图,你可以看到黑色单元格不在中间。是的,可以改变中心。您没有描述到达边界时的行为,因此术语
floor(min(center./window_size))*2+1
可能需要更改。我使用以下方法进行了更正:对于blockindex=1:size(blocks,2)block=rand(W(1),W(2));M(块(1,块索引):块(1,块索引)+W(1)-1,块(2,块索引):块(2,块索引)+W(2)-1)=块;图像sc(M);轴等紧xy暂停(.1)endNice非常聪明!再加上你正在使用
1j
作为虚拟单位:)@Benoit_11谢谢!我喜欢用复数自然地解决一个问题:-)同意这很优雅!我把这个问题作为你最喜欢的回答。如何在脚本中使用所描述的参数?(OP,网格大小)您已经考虑了原点和步长,但我还需要考虑OP和网格大小。@山姆:您必须将
step
设置为
gridsize OP
。生成左下角时,仅与到下一个左下角的距离相关。
%// Data
step = 3;     %// step size
overlap = 1;  %// overlap
x0 = 20;      %// x coordinate of origin
y0 = 15;      %// y coordinate of origin
xmin = 0;     %// window boundary: min x
xmax = 40;    %// window boundary: max x
ymax = 30;    %// window boundary: min y
ymin = 0;     %// window boundary: max y

%// Computations
stepov = step-overlap;
N = 8; %// Initial value. Will be increased as needed
done = false;
while ~done
    z = x0+1j*y0 + stepov*cumsum([0 -1j.^(-floor(sqrt(4*(0:N)+1))-1)]);
        %// compute coordinates of N points
    ind = find(real(z)<xmin | real(z)>xmax | imag(z)<ymin | imag(z)>ymax, 1);
        %// find index of first z out of boundary, if any
    done = ~isempty(ind); %// exit if we have reached outside window boundary
    N = N*2; %// increase number of steps for next try
end
z = z(1:ind-1); %// only keep values that are within the boundary
x = real(z);
y = imag(z);