您的位置:首页 > 其它

usaco 4.3.2 The Primes

2010-12-25 11:30 162 查看
开始的时候自己写的代码最多只能过7组数据。我一直想不把输出存起来,直接找到一个就输出,这样的话就只能一行一行枚举,这样的话填的时候限制条件就很少了。搞到最后所有可以想到的剪枝都用了,还是只能过7组数据。没办法只好搜一下解题报告,原来别人都是把输出存起来的。这样的话限制条件就多了。

填表顺序:

第一行,第一列;

左下到右上;

左上到右下;

第二行,第二列,第四行,第四列;

第三行,第三列;

这样的顺序就是为了使限制条件尽可能的多。

自己完全没有想到。

代码:

/*
ID: mnlm1991
PROG: prime3
LANG: C++
*/

#include<cstdio>
#include<cstdlib>
#include<cmath>
#include<cstring>
#include<vector>
#include<algorithm>
#include<string>
#include<map>
#include<set>
#include<bitset>
#include<queue>
#include<iostream>

using namespace std;

const int MaxN = 100002;
const int M = 10000;
const int mod[] = {10000, 1000, 100, 10, 1};
int prm[M];
bool is[MaxN];
int sum;
int start;
int N;
int pos[MaxN + 1];
bool flag;
struct ANS
{
int tt[5][5];
bool operator < (const ANS & other) const
{
int i;
int j;
for (i = 0; i < 5; i++)
{
for (j = 0; j < 5; j++)
{
if (tt[i][j] != other.tt[i][j])
{
return tt[i][j] < other.tt[i][j];
}
}
}
return false;
}
};
ANS ans[10000];
ANS tmp;
int cnt;
int DigitSum(int x)
{
int ret = 0;
while (x)
{
ret += x % 10;
x /= 10;
}
return ret;
}
bool Digit(int x)
{
while (x)
{
if (x % 10 == 0)
{
return false;
}
x /= 10;
}
return true;
}
int d[5];
void getpos(int x, int k)
{
if (x < M)
{
return;
}
pos[x] = k;
return;
}
int getprm(int n)
{
int i, j, k = 0;
int s;
int e = (int)(sqrt(0.0 + n) + 1);
memset(is, 1, sizeof(is));
memset(pos, -1, sizeof(pos));
for (i = 4; i < n; i += 2)
{
is[i] = 0;
}
int x;
for (i = 3; i < e; i += 2)
{
getpos(i, k);
if (is[i])
{
if (i >= M && DigitSum(i) == sum)
{
prm[k++] = i;
}
else
{
is[i] = false;
}
for (s = i * 2, j = i * i; j < n; j += s)
{
is[j] = 0;
}
}
}
for (i = max(i, M + 1); i < n; i += 2 )
{
getpos(i, k);
getpos(i - 1, k);
if (is[i] && DigitSum(i) == sum)
{
prm[k++] = i;
}
else
{
is[i] = false;
}
}
return k;
}
int table[5][5];
int p1[100000];
int p15[10][10][1000];
int p13[10][10][1000];
int p124[10][10][10][100];
void Init()
{
memset(p1, -1, sizeof(p1));
int i;
int j = 0;
for (i = pos[start * mod[0]]; i < pos[(start + 1)* mod[0]]; i++)
{
if (Digit(prm[i]))
{
p1[j++] = prm[i];
}
}
int k;
int l;
int w;
memset(p15, -1, sizeof(p15));
for (i = 1; i < 10; i++)
{
for (j = 0; j < 10; j++)
{
l = 0;
for (k = pos[i * mod[0]]; k < pos[(i + 1)* mod[0]]; k++)
{
if (prm[k] % 10 == j)
{
p15[i][j][l++] = prm[k];
}
}
}
}
memset(p13, -1, sizeof(p13));
for (i = 1; i < 10; i++)
{
for (j = 0; j < 10; j++)
{
l = 0;
for (k = pos[i * mod[0]]; k < pos[(i + 1)* mod[0]]; k++)
{
if (prm[k] / mod[2] % 10 == j)
{
p13[i][j][l++] = prm[k];
}
}
}
}
memset(p124, -1, sizeof(p124));
for (i = 1; i < 10; i++)
{
for (j = 0; j < 10; j++)
{
for (k = 0; k < 10; k++)
{
l = 0;
for (w = pos[(i * 10 + j)* 1000]; w < pos[(i * 10 + j + 1)* 1000]; w++)
{
if (prm[w] / mod[3] % 10 == k)
{
p124[i][j][k][l++] = prm[w];
}
}
}
}
}
return;
}
void DFS(int kk)
{
int i;
int j;
int k;
int t;
int l;
switch (kk)
{
case 0 :
for (i = 0; p1[i] != -1; i++)
{
t = p1[i];
for (k = 4; k >= 0; k--)
{
table[0][k] = t % 10;
t /= 10;
}
for (j = 0; p1[j] != -1; j++)
{
t = p1[j];
for (k = 4; k > 0; k--)
{
table[k][0] = t % 10;
t /= 10;
}
DFS(kk + 1);
}
}
break;
case 1 :
for (i = 0; p15[table[4][0]][table[0][4]][i] != -1; i++)
{
t = p15[table[4][0]][table[0][4]][i];
for (j = 1; j < 4; j++)
{
table[4 - j][j] = t / mod[j] % 10;
}
DFS(kk + 1);
}
break;
case 2 :
for (i = 0; p13[table[0][0]][table[2][2]][i] != -1; i++)
{
t = p13[table[0][0]][table[2][2]][i];
for (j = 1; j < 5; j++)
{
table[j][j] = t / mod[j] % 10;
}
DFS(kk + 1);
}
break;
case 3 :
for (i = 0; p124[table[1][0]][table[1][1]][table[1][3]][i] != -1; i++)
{
t = p124[table[1][0]][table[1][1]][table[1][3]][i];
table[1][2] = t / mod[2] % 10;
table[1][4] = t / mod[4] % 10;
for (j = 0; p124[table[0][1]][table[1][1]][table[3][1]][j] != -1; j++)
{
t = p124[table[0][1]][table[1][1]][table[3][1]][j];
table[2][1] = t / mod[2] % 10;
table[4][1] = t / mod[4] % 10;
DFS(kk + 1);
}
}
break;
case 4 :
for (i = 0; p124[table[3][0]][table[3][1]][table[3][3]][i] != -1; i++)
{
t = p124[table[3][0]][table[3][1]][table[3][3]][i];
table[3][2] = t / mod[2] % 10;
table[3][4] = t / mod[4] % 10;
for (j = 0; p124[table[0][3]][table[1][3]][table[3][3]][j] != -1; j++)
{
t = p124[table[0][3]][table[1][3]][table[3][3]][j];
table[2][3] = t / mod[2] % 10;
table[4][3] = t / mod[4] % 10;
DFS(kk + 1);
}
}
break;
case 5 :
t = 0;
for (i = 0; i < 4; i++)
{
t = t * 10 + table[2][i];
}
t *= 10;
l = 0;
for (i = 0; i < 4; i++)
{
l = l * 10 + table[i][2];
}
l *= 10;
for (i = pos[t]; i < pos[t + 10]; i++)
{
table[2][4] = prm[i] % 10;
for (j = pos[l]; j < pos[l + 10]; j++)
{
table[4][2] = prm[j] % 10;
DFS(kk + 1);
}
}
break;
case 6 :
t = 0;
l = 0;
for (i = 0; i < 5; i++)
{
t = t * 10 + table[4][i];
l = l * 10 + table[i][4];
}
if (is[t] && is[l])
{
memcpy(ans[cnt].tt, table, sizeof(table));
cnt++;
}
break;
default : ;
}
return;
}
int main()
{
freopen("prime3.in", "r", stdin);
freopen("prime3.out", "w", stdout);
while (scanf("%d%d", &sum, &start) != EOF)
{
int N = getprm(MaxN);
Init();
cnt = 0;
DFS(0);
if (!cnt)
{
printf("NONE/n");
}
else
{
int i;
int j;
int k;
sort(ans, ans + cnt);
for (i = 0; i < cnt; i++)
{
if (i)
{
printf("/n");
}
for (j = 0; j < 5; j++)
{
for (k = 0; k < 5; k++)
{
printf("%d", ans[i].tt[j][k]);
}
printf("/n");
}
}
}
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: