可能重复:
Looping in a spiral
Writing a string in a spiral
Print two-dimensional array in spiral order
2d Array in Spiral Order
我们有一个矩阵
形式的数据0 0 0 0 0
0 1 2 3 0
0 4 5 6 0
0 7 8 9 0
0 0 0 0 0
以这种方式存储在1d数组中
[0 0 0 0 0 0 1 2 3 0 0 4 5 6 0 0 7 8 9 0 0 0 0 0 0]
这是一个零填充的3x3阵列转换为5x5。我们知道起始索引和结束索引。
正如我们所看到的,我们可以执行25次操作并打印所有值,但是如果我们按螺旋顺序排列,我们理想情况下应该只执行9次操作。
有谁知道怎么做?
我们知道行数和列数。这里是行= 5 cols = 5.
因此,起始索引将是行+ 1,而结束索引将是行* cols-6
我将其视为螺旋顺序遍历。
答案 0 :(得分:0)
假设您的5x5
矩阵假设零指数基数,您知道行索引是:
0,1,2,3,4
5,6,7,8,9
10,11,12,13,14
15,16,17,18,19
20,21,22,23,24
您知道您的第一个索引是6
,而最后一个索引是18
。因此,作为一个起点,您知道可以消除矩阵的以下部分:
0,1,2,3,4
和
19,20,21,22,23,24,25
这算作2
次操作。
你也知道,既然你是从索引6
开始而且它是3x3
,你只需要去索引8
,这是一个操作。
然后,您需要将5
添加到之前的6
索引中,这会产生11
并再次继续(总计2
次操作)当前操作计数为{{1 }})
使用5
再次执行此操作,即可获得11
个操作。再获得2项操作,最终得到16
。现在共有8个操作。
答案 1 :(得分:0)
我会做这样的事情:
POINT ul = (start_idx/width, start_idx%width);
POINT br = (end_idx/width, end_idx%width);
POINT p = ul
dir = RIGHT;
while (ul != br)
visit(ARRAY[p.x+p.y*WIDTH])
case dir
when RIGHT:
p.x+=1
if (p.x==br.x)
dir = DOWN
ul.y++;
when DOWN
p.y+=1
if (p.y==br.y)
dir = LEFT
br.x--;
when LEFT:
//like RIGHT but -1 and adjust br.y upwards when done
when UP:
//like DOWN but -1 and adjust ul.x rightward when done
endwhile
想法是跟踪要访问的虚拟x和y。移动点以沿着由起点和终点定义的框的侧面进行访问。在完成访问时调整两侧。