题目大意
已知多项式方程:a0+a1x+a2x^2+..+anx^n=0求这个方程在[1, m ] 内的整数解(n 和m 均为正整数)ai<=10^10000
题解
枚举多个不太大的质数$p_i$,枚举$xin[0,p_i-1]$,预处理,用秦九韶算法看看$f(x)$是否为0(f运算时取模)。多枚举几个质数进行上述操作,对于$xin [1,m]$,若对$forall p_i, f(xmathrm{mod}p_i)=0$,则$x$为一个解。
注意。如果枚举的$p_i$是个大质数,枚举$xin[1,m]$在线判断$f(xmathrm{mod}p_i)=0$,只能得70分。
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
#define ll long long
const int P[4] = {23333, 10007, 10003, 27777};
const int TotP = 4;
const int MAX_STR_LEN = 10010;
const int MAX_N = 110;
const int MAX_M = 1000010;
const int MAX_P = 30000;
char S[MAX_N][MAX_STR_LEN];
ll A[MAX_N];
bool Mod_IsSol[MAX_P];
bool IsSol[MAX_M];
int M, N;
ll ReadMod(const char *s, const ll p)
{
int len = strlen(s);
int ans = 0, f = 1;
for (int i = 0; i < len; i++)
{
if (s[i] == '-')
{
f = -1;
continue;
}
ans = (ans * 10 + s[i] - '0') % p;
}
return ans * f;
}
bool Feq0(const ll x, const ll p, const ll *a, const int n)
{
ll cur = 0;
for (int i = n; i >= 0; i--)
cur = (cur * x + a[i]) % p;
return cur == 0;
}
void Select(const ll p)
{
memset(Mod_IsSol, false, sizeof(Mod_IsSol));
for (int i = 0; i <= N; i++)
A[i] = ReadMod(S[i], p);
for (int i = 0; i < p; i++)
if (Feq0(i, p, A, N))
Mod_IsSol[i] = true;
for (int i = 1; i <= M; i++)
if (!Mod_IsSol[i % p])
IsSol[i] = false;
}
int main()
{
scanf("%d%d
", &N, &M);
for (int i = 0; i <= N; i++)
scanf("%s", S[i]);
for (int i = 1; i <= M; i++)
IsSol[i] = true;
for (int i = 0; i < TotP; i++)
Select(P[i]);
int cnt = 0;
for (int i = 1; i <= M; i++)
cnt += IsSol[i];
printf("%d
", cnt);
for (int i = 1; i <= M; i++)
if (IsSol[i])
printf("%d
", i);
return 0;
}