初看很难 其实很简单的一道题目
大致就是1-n 把这n个数填到一个环里 相邻的和是素数 求怎么填
我开始的时候 觉得要顺时针还要逆时针 心想繁琐 就直接找了博客 然后博客的代码异常简洁啊
突然领悟了 逆时针的只要水平翻转一下一样是个顺时针的 也就是说 这个逆时针已经在所有情况里了
然后这个题 其实也是那种 案例过了就很难再有问题的题
问题是我开始的时候的打的那一边怎么都过不了案例 为什么呢 因为vis标错对象了
我们的代码思路很简单 num是层数 是数字安放的位置 i是数字 一个个看这个数字可不可以放在这里 如果遍历一遍1-n所有数字都不可以放在这 那么就返回上一层 不然就继续下一个位置
其中就需要判断一个数字有没有放过 而我判断的是这个位置有没有数字存在 这需要判断吗 不需要……所以找了半天错了
然后 然后我reac 再次惊讶到了 我觉得我理解了比较OK了 然而 当然对比一下昨天的代码就可以很明显的知道问题
dfs传参数的时候 传的是num 而我一旦使用了自增 那么在这一层的num都会受到影响 所以 不可以!
开始我用的num++(日常秀逗) 后来惊呼 传进去的都是自增前的 然后换成++num 结果也不ok 原因如上
希望能长点记性把
#include <iostream>
#include <string>
#include <cstring>
#include <sstream>
#include <algorithm>
#include <vector>
#include <queue>
#include <map>
#include <cmath>
using namespace std;
int isp[50];
int a[50], vis[50];
int n;
void pri()
{
for (int i = 2; i < 50; i++)
{
if (isp[i] == 0)
{
for (int j = i; i*j < 50; j++)
{
isp[j*i] = 1;
}
}
}
}
void dfs(int num)
{
if (n == num && isp[a[0] + a[n - 1]] == 0)
{
for (int i = 0; i < n; i++)
{
cout << a[i] << (i == n - 1 ? "\n" : " ");
}
}
else
{
for (int i = 2; i <= n; i++)
{
if (vis[i] == 0 && isp[i + a[num - 1]]==0)
{
vis[i] = 1;
a[num] = i;
dfs(num+1);//绝对不能用++ 自增
vis[i] = 0;
}
}
}
}
int main()
{
pri();
int cas = 0;
while (cin >> n)
{
printf("Case %d:\n", ++cas);
memset(vis, 0, sizeof(vis));
memset(a, 0, sizeof(a));
a[0] = 1;
dfs(1);
cout << endl;
}
system("pause");
return 0;
}