Задача: Заполнить массив размерности NxM числами 1, 2, 3, … по спирали, начиная с правого верхнего угла. (При заполнении массива двигаться по часовой стрелке).
Перед тем как привести фрагмент кода добавим, что… Вначале мы будем заполнять горизонтальную строку с первого по третий (для общего случая по предпоследний), затем последний столбец с первой строки по… правильно, по предпоследнюю. Затем заполним нижнюю горизонтальную (7-9) в обратном порядке и левую вертикальную снизу вверх (10-12).
Реализация на языке Pascal:
Program tip; uses crt; Var a:array[1..4,1..4] of integer; z,krug,g1,g2,g3,g4,N,i,j:integer; Begin clrscr; N:=4; z:=1; {цикл, который отвечате за количество витков спирали} for krug:=1 to ((n+1) div 2) do begin {цикл, верхней горизотальной части витка} for g1:=krug to N-krug do begin a[krug,g1]:=z; inc(z); end; {цикл, правой вертикальной части витка (той, что сверху вниз)} for g2:=krug to N-krug do begin a[g2,((n+1)-krug)]:=z; inc(z); end; {цикл, нижней горизонтальной части витка (той, что справа налево)} for g3:=((N+1)-krug) downto krug+1 do begin a[((N+1)-krug),g3]:=z; inc(z); end; {цикл, левой вертикальной части витка (той, что снизу вверх)} for g4:=((N+1)-krug) downto krug+1 do begin a[g4,krug]:=z; inc(z); end; end; for i:=1 to 4 do begin Writeln; for j:=1 to 4 do Write(a[i,j]:5); end; readln; End.
На PascalABC
ВідповістиВидалити//Матрица по спирали из любого угла или из центра, по часовой или против часовой
begin
var n:= 3;
var ИзЦентра := 0; // 0 - из угла 1 - из Центра
Var Центр := Ceil(n / 2) - 1; //Координата центра матрицы
var (i, j, Направление, nEven) := (0, 0, 1, n.IsEven ? 1 : 0); // с левого верхнего
if ИзЦентра = 1 then (i, j, Направление, nEven) := (Центр, Центр, 1, 0); // из центра
var Матрица := new integer[n,n];
for var Элемент := 1 to n*n do
begin
Матрица[i, j] := Элемент; {
[i,j] - с левого верхнего по часовой
[j,i] - с левого верхнего против часовой
[n-1-i,j] - с левого нижнего против часовой
[n-1-j,i] - с левого нижнего по часовой
[j,n-1-i] - с правго верхнего по часовой
[i,n-1-j] - c правго верхнего против часовой
[n-1-i,n-1-j] - c правого нижнего по часовой
[n-1-j,n-1-i] - c правого нижнего против часовой
}
case Направление of
1:begin {вправо}
inc(j);
if (Центр - i + ИзЦентра ) = (j - Центр - nEven) then Направление := 2;
end;
2:begin {вниз}
inc(i);
if i = j then Направление := 3;
end;
3:begin {влево}
dec(j);
if (i - Центр) = (Центр - j + nEven) then Направление := 4;
end;
4:begin {вверх}
dec(i);
if (i - 1) = (j - ИзЦентра) then Направление := 1;
end
end;
end;
Матрица.Println;
end.
На PascalABC.net
Видалитиbegin
var n := 5; // от 2 (2 на 2) и более
var a := new integer[n, n];
var (i, j, c) := (0, -1, 1);
repeat
loop n do begin inc(j); a[i, j] := c; inc(c) end;
loop n - 1 do begin inc(i); a[i, j] := c; inc(c) end;
loop n - 1 do begin dec(j); a[i, j] := c; inc(c) end;
loop n - 2 do begin dec(i); a[i, j] := c; inc(c) end;
dec(n, 2);
until n < 1;
a.Println
end.
Квадратная и Неквадратаня Матрица по спирали на PascalABC.NET
ВідповістиВидалитиbegin
var (n, m) := (5, 4);
var a := new integer[n, m];
var (i, j, c, ii, jj) := (0, 0, 1, 0, 1);
repeat
a[i, j] := c;
if not ((i + ii in 0..n - 1) and (j + jj in 0..m - 1) and (a[i + ii, j + jj] = 0)) then (ii, jj) := ii = 0 ? (jj, 0) : (0, -ii); //поворот направо
(i, j, c) := (i + ii, j + jj, c + 1);
until c > n * m;
a.Println
end
begin//матрица 4х6 по спирали
ВідповістиВидалитиvar (n, m) := (4, 6);
var a := new integer[n, m];
var (i, j, c, d) := (0, -1, 1, 1);
repeat
loop m do begin j += d; a[i, j] := c; c += 1 end;
loop n - 1 do begin i += d; a[i, j] := c; c += 1 end;
m -= 1; n -= 1; d := -d;
until (n = 0) or (m = 0);
a.Println
end.
## //Матрица произвольного размера по спирали через индексы
ВідповістиВидалитиvar (n,m) := (6,4); //например 6х4
var a := new integer[n,m];
for var i := 0 to n-1 do
for var j := 0 to m-1 do begin
var x := min(i,j,n-1 - i, m-1 - j);
a[i,j] := n*m+1 - if (i>x) and (m-1-j>x) then (n-2*x-2)*(m-2*x-2) + (i-x) + (j-x)
else (n-2*x)*(m-2*x) - (i-x) - (j-x)
end;
a.Println
begin
ВідповістиВидалитиvar (n,m) := (3,5);
var a := new integer[n,m];
var (i,j,di,dj,k) := (0,0,0,1,0);
for var c := 1 to n*m do begin
a[i,j] := c;
if (i, di) = (k+1, -1) then k+=1; //переход в след.спираль
if k>min(i+di,j+dj,n-1-i-di,m-1-j-dj) then //выход зв спираль?
(di,dj):= di=0? (dj,0):(0,-di); //поворот направо
i+=di; j+=dj
end;
a.Println
end.