21 22................
20 7 8 9 10
19 6 1 2 11
18 5 4 3 12
17 16 15 14 13
的矩阵。
问题有两个:
1. 编程实现输出这个矩阵
2. 设1点的坐标是(0,0),x方向向右为正,y方向向下为正.例如:7的坐标为(-1,-1) ,2的坐标为(0,1),3的坐标为(1,1).编程实现输入任意一点坐标(x,y),输出所对应的数字。
1. 第一个问题我是采用模拟进行构造的,可以看到从1开始的方向变化始终是 right->down->left->up,
所持续 走的长度为1->1->2->2->3->3->...,发现了这个规律不难写出代码了!注意下面我把1的位置设置
在((n-1)/2, (n-1)/2)的位置。
代码
1 void Simulate(int n)
2 {
3 int x, y;
4 x = y = (n - 1) / 2; //1的位置
5 data[x][y] = 1;
6 int len = 1;
7 int count = 0;
8 int num = 2;
9 DIRECTION dir = RIGHT;
10 while(num <= n * n)
11 {
12 for(int i = 0; i < len; i++)
13 {
14 switch(dir)
15 {
16 case LEFT:
17 --y; break;
18 case RIGHT:
19 ++y; break;
20 case UP:
21 --x; break;
22 case DOWN:
23 ++x; break;
24 default: break;
25 }
26 data[x][y] = num++;
27 }
28 count++;
29 if(count == 2)
30 {
31 count = 0;
32 len++;
33 }
34 dir = (DIRECTION)((dir + 1) % 4);
35 }
36 }
2 {
3 int x, y;
4 x = y = (n - 1) / 2; //1的位置
5 data[x][y] = 1;
6 int len = 1;
7 int count = 0;
8 int num = 2;
9 DIRECTION dir = RIGHT;
10 while(num <= n * n)
11 {
12 for(int i = 0; i < len; i++)
13 {
14 switch(dir)
15 {
16 case LEFT:
17 --y; break;
18 case RIGHT:
19 ++y; break;
20 case UP:
21 --x; break;
22 case DOWN:
23 ++x; break;
24 default: break;
25 }
26 data[x][y] = num++;
27 }
28 count++;
29 if(count == 2)
30 {
31 count = 0;
32 len++;
33 }
34 dir = (DIRECTION)((dir + 1) % 4);
35 }
36 }
2. 第二个问题我也是先找出规律,然后进行模拟。
首先,不难看出n*n的螺旋矩阵的右下角的坐标一定是(m, m),这里m=n-1
通 过观察,可以看出 n=1的时候,右下角(0,0)的值为1,当n=2的时候,右下角(1,1)的坐标值为(3,3),当n=3的时候,右下角(2,2)的坐标值为13.直 觉告诉我,这个值是关于n的二次函数,设f(n) = a*n^2 + b*n + c
联立方程组,可以求得a,b,c。 最终算出来的f(n) = 4*n^2 - 2*n + 1
下面再根据(x,y)和右下角(n-1,n-1)之间的关系,计算出值即可。这里要注意当x的值与n-1相 同时,应优先考虑y与-m是否有联系。这就要求在函数中要注意x,y的判断先后顺序了。
代码如下:
代码
1 //以(1,1)所在位置作为原点,向右作为x正半轴,向下作为y正半轴
2 int GetValue(int x, int y)
3 {
4 int m = max(abs(x), abs(y));
5 int rightBottom = m * m * 4 - 2 * m + 1;
6 int value = 0;
7 if(x == -m)
8 {
9 value = rightBottom + 2 * m + m - y;
10 }
11 else if( y == m)
12 {
13 value = rightBottom + m - x;
14 }
15 else if(y == -m)
16 {
17 value = rightBottom + 4 * m + x + m;
18 }
19 else if( x == m )
20 {
21 value = rightBottom - (m - y);
22 }
23
24
25 return value;
26 }
2 int GetValue(int x, int y)
3 {
4 int m = max(abs(x), abs(y));
5 int rightBottom = m * m * 4 - 2 * m + 1;
6 int value = 0;
7 if(x == -m)
8 {
9 value = rightBottom + 2 * m + m - y;
10 }
11 else if( y == m)
12 {
13 value = rightBottom + m - x;
14 }
15 else if(y == -m)
16 {
17 value = rightBottom + 4 * m + x + m;
18 }
19 else if( x == m )
20 {
21 value = rightBottom - (m - y);
22 }
23
24
25 return value;
26 }
完整代码如下:
代码
1 #include <iostream>
2 #include <cstdlib>
3 #include <algorithm>
4
5 using namespace std;
6
7 const int N = 100;
8
9 int data[N + 1][N + 1];
10
11 enum DIRECTION
12 {
13 RIGHT, DOWN , LEFT, UP
14 };
15
16 //模拟整个过程
17 void Simulate(int n)
18 {
19 int x, y;
20 x = y = (n - 1) / 2; //1的位置
21 data[x][y] = 1;
22 int len = 1;
23 int count = 0;
24 int num = 2;
25 DIRECTION dir = RIGHT;
26 while(num <= n * n)
27 {
28 for(int i = 0; i < len; i++)
29 {
30 switch(dir)
31 {
32 case LEFT:
33 --y; break;
34 case RIGHT:
35 ++y; break;
36 case UP:
37 --x; break;
38 case DOWN:
39 ++x; break;
40 default: break;
41 }
42 data[x][y] = num++;
43 }
44 count++;
45 if(count == 2)
46 {
47 count = 0;
48 len++;
49 }
50 dir = (DIRECTION)((dir + 1) % 4);
51 }
52 }
53
54 //打印螺旋矩阵
55 void Output(int n)
56 {
57 int i, j;
58 for(i = 0; i < n; i++)
59 {
60 cout << data[i][0];
61 for(j = 1; j < n; j++)
62 cout << "\t" << data[i][j];
63 cout << endl;
64 }
65 }
66
67 //以(1,1)所在位置作为原点,向右作为x正半轴,向下作为y正半轴
68 int GetValue(int x, int y)
69 {
70 int m = max(abs(x), abs(y));
71 int rightBottom = m * m * 4 - 2 * m + 1;
72 int value = 0;
73 if(x == -m)
74 {
75 value = rightBottom + 2 * m + m - y;
76 }
77 else if( y == m)
78 {
79 value = rightBottom + m - x;
80 }
81 else if(y == -m)
82 {
83 value = rightBottom + 4 * m + x + m;
84 }
85 else if( x == m )
86 {
87 value = rightBottom - (m - y);
88 }
89
90
91 return value;
92 }
93
94 void TestPos(int n)
95 {
96 int i, j;
97 for(i = 0; i < n; i++)
98 {
99 cout << GetValue(0 - (n - 1) / 2, i - (n - 1) / 2);
100 for(j = 1; j < n; j++)
101 cout << "\t" << GetValue(j - (n - 1) / 2, i - (n - 1) / 2);
102 cout << endl;
103 }
104 }
105
106 int main()
107 {
108 int n;
109 while(cin >> n)
110 {
111 if(n <= 0 || n > 100)
112 {
113 cerr << "Size error!" << endl;
114 break;
115 }
116 else
117 {
118 Simulate(n);
119 Output(n);
120 cout << "*******************" << endl;
121 TestPos(n);
122 }
123 }
124
125 return 0;
126 }
2 #include <cstdlib>
3 #include <algorithm>
4
5 using namespace std;
6
7 const int N = 100;
8
9 int data[N + 1][N + 1];
10
11 enum DIRECTION
12 {
13 RIGHT, DOWN , LEFT, UP
14 };
15
16 //模拟整个过程
17 void Simulate(int n)
18 {
19 int x, y;
20 x = y = (n - 1) / 2; //1的位置
21 data[x][y] = 1;
22 int len = 1;
23 int count = 0;
24 int num = 2;
25 DIRECTION dir = RIGHT;
26 while(num <= n * n)
27 {
28 for(int i = 0; i < len; i++)
29 {
30 switch(dir)
31 {
32 case LEFT:
33 --y; break;
34 case RIGHT:
35 ++y; break;
36 case UP:
37 --x; break;
38 case DOWN:
39 ++x; break;
40 default: break;
41 }
42 data[x][y] = num++;
43 }
44 count++;
45 if(count == 2)
46 {
47 count = 0;
48 len++;
49 }
50 dir = (DIRECTION)((dir + 1) % 4);
51 }
52 }
53
54 //打印螺旋矩阵
55 void Output(int n)
56 {
57 int i, j;
58 for(i = 0; i < n; i++)
59 {
60 cout << data[i][0];
61 for(j = 1; j < n; j++)
62 cout << "\t" << data[i][j];
63 cout << endl;
64 }
65 }
66
67 //以(1,1)所在位置作为原点,向右作为x正半轴,向下作为y正半轴
68 int GetValue(int x, int y)
69 {
70 int m = max(abs(x), abs(y));
71 int rightBottom = m * m * 4 - 2 * m + 1;
72 int value = 0;
73 if(x == -m)
74 {
75 value = rightBottom + 2 * m + m - y;
76 }
77 else if( y == m)
78 {
79 value = rightBottom + m - x;
80 }
81 else if(y == -m)
82 {
83 value = rightBottom + 4 * m + x + m;
84 }
85 else if( x == m )
86 {
87 value = rightBottom - (m - y);
88 }
89
90
91 return value;
92 }
93
94 void TestPos(int n)
95 {
96 int i, j;
97 for(i = 0; i < n; i++)
98 {
99 cout << GetValue(0 - (n - 1) / 2, i - (n - 1) / 2);
100 for(j = 1; j < n; j++)
101 cout << "\t" << GetValue(j - (n - 1) / 2, i - (n - 1) / 2);
102 cout << endl;
103 }
104 }
105
106 int main()
107 {
108 int n;
109 while(cin >> n)
110 {
111 if(n <= 0 || n > 100)
112 {
113 cerr << "Size error!" << endl;
114 break;
115 }
116 else
117 {
118 Simulate(n);
119 Output(n);
120 cout << "*******************" << endl;
121 TestPos(n);
122 }
123 }
124
125 return 0;
126 }