题目
Time Limit: 5000 ms
Memory Limit: 128 MB
Total Submission: 146
Submission Accepted: 34Description
给定两个长度均为3的数字序列,每位上为一个范围是1-N的正整数,求有多少个仍然由3个1-N的整数构成的数字序列能与给定的两个序列中的任意一个匹配。
如果两个序列匹配,当且仅当两个序列中的每个对应数字的最近距离不超过2。
比如当N为9时,每一位数字可能是1,2,3,4,5,6,7,8,9,并且数字是循环的。也就是说9和1是相邻的。
数字之间的距离就是两个数字的位置之差。
也就是说在上面的例子中,9和1的最近距离是1,9和2的最近距离是2,2和5的最近距离是3。
比如现在给定两个序列组合为(1,2,3)和(4,5,6), (2,4,8)或者(1, N, 5) 是能和两个序列匹配中的至少一个匹配的,但是(1, 5, 6)是不能和给定的两个序列中的任何一个匹配的。Input
多组输入,以EOF结束。
每组输入包含三行第一行为一个整数N(1 <= N <= 50),第二行和第三行都是以三个空格分隔的整数。Output
对于每组输入,输出一个数字,表示能和给定的两个序列中的任意一个匹配的序列的个数。
Sample Input
50
1 2 3
5 6 7Sample Output
249
Source
Roll
题解
建立一个三维坐标系,把能覆盖到的地方全部标记上,然后计算数量
其中要注意小于等于0和大于N的情况(转换后还应该在0-N之间)。
代码
/* By:OhYee Github:OhYee Email:oyohyee@oyohyee.com */ #include <cstdio> using namespace std; const int maxn = 55; bool Do() { int N,a1,b1,c1,a2,b2,c2; int cnt = 0; if(scanf("%d%d%d%d%d%d%d",&N,&a1,&b1,&c1,&a2,&b2,&c2) == EOF) return false; bool map[maxn][maxn][maxn] = {0}; for(int x = a1 - 2;x <= a1 + 2;x++) for(int y = b1 - 2;y <= b1 + 2;y++) for(int z = c1 - 2;z <= c1 + 2;z++) { int xx = x <= 0 ? N + x : x > N ? x - N : x; int yy = y <= 0 ? N + y : y > N ? y - N : y; int zz = z <= 0 ? N + z : z > N ? z - N : z; if(!map[xx][yy][zz] && xx > 0 && xx <= N&&yy > 0 && yy <= N&&zz > 0 && zz <= N) cnt++; map[xx][yy][zz] = 1; } for(int x = a2 - 2;x <= a2 + 2;x++) for(int y = b2 - 2;y <= b2 + 2;y++) for(int z = c2 - 2;z <= c2 + 2;z++) { int xx = x <= 0 ? N + x : x > N ? x - N : x; int yy = y <= 0 ? N + y : y > N ? y - N : y; int zz = z <= 0 ? N + z : z > N ? z - N : z; if(!map[xx][yy][zz] && xx > 0 && xx <= N&&yy > 0 && yy <= N&&zz > 0 && zz <= N) cnt++; } printf("%d\n",cnt); return true; } int main() { while(Do()); return 0; }