QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#202411#6399. Classic: Classical Problemucup-team870WA 1ms10116kbC++204.7kb2023-10-06 01:13:302023-10-06 01:13:30

Judging History

你现在查看的是最新测评结果

  • [2023-10-06 01:13:30]
  • 评测
  • 测评结果:WA
  • 用时:1ms
  • 内存:10116kb
  • [2023-10-06 01:13:30]
  • 提交

answer

#include<bits/stdc++.h>
using namespace std;
#define IOS {cin.tie(0);cout.tie(0);ios::sync_with_stdio(0);}
#define rep(i,j,k) for(int i=j;i<=k;++i)
#define per(i,j,k) for(int i=j;i>=k;--i)
#define P pair<int,int>
#define ll long long
#define vi vector<int>
#define db double
const int N=2e5+5;
namespace MTT { //任意模数多项式乘法. 无需long double
    typedef vi poly;
	int mod; const db pi = acos(-1.0);
	struct cp {
		db r, i;
		cp() {}
		cp(const db& _r, const db& _i) :r(_r), i(_i) {}
	};
	inline cp operator + (const cp& a, const cp& b) { return cp(a.r + b.r, a.i + b.i); }
	inline cp operator - (const cp& a, const cp& b) { return cp(a.r - b.r, a.i - b.i); }
	inline cp operator * (const cp& a, const cp& b) { return cp(a.r * b.r - a.i * b.i, a.r * b.i + a.i * b.r); }
	inline cp operator / (const cp& a, const db& b) { return cp(a.r / b, a.i / b); }
	inline cp conj(const cp& a) { return cp(a.r, -a.i); }
	int rev[N * 4]; cp Wn[N * 4]; int Now_Len;
	inline void revinit(int n) {
		for (int i = 0; i < n; ++i)rev[i] = (rev[i >> 1] >> 1) | ((i & 1) * (n >> 1));
		for (int i = 0; i < n; ++i)Wn[i] = cp(cos(pi * i / n), sin(pi * i / n));
		Now_Len = n;
	}
	inline void DFT(cp* A, int n) {
		if (Now_Len != n)revinit(n);
		for (int i = 0; i < n; ++i)if (i < rev[i])swap(A[i], A[rev[i]]);
		for (int i = 1; i < n; i <<= 1) {
			for (int j = 0; j < n; j += i << 1) {
				for (int k = 0; k < i; ++k) {
					cp u = A[j + k], v = A[i + j + k] * Wn[n / i * k];
					A[j + k] = u + v; A[i + j + k] = u - v;
				}
			}
		}
	}
	inline void IDFT(cp* A, int n) {
		if (Now_Len != n)revinit(n);
		for (int i = 0; i < n; ++i)if (i < rev[i])swap(A[i], A[rev[i]]);
		for (int i = 1; i < n; i <<= 1) {
			for (int j = 0; j < n; j += i << 1) {
				for (int k = 0; k < i; ++k) {
					cp u = A[j + k], v = A[i + j + k] * conj(Wn[n / i * k]);
					A[j + k] = u + v;
					A[i + j + k] = u - v;
				}
			}
		}
		for (int i = 0; i < n; ++i)A[i] = A[i] / n;
	}
	cp Ta[N * 4], Tb[N * 4], Tc[N * 4], Td[N * 4];
	poly MTT(poly& A, poly& B) {
		int lenA = A.size(), lenB = B.size();
		int lenC = lenA + lenB - 1, n;
		for (n = 1; n < lenC; n <<= 1);
		poly C(n);
		for (int i = 0; i < lenA; ++i)Ta[i] = cp(A[i] & 32767, A[i] >> 15);
		for (int i = 0; i < lenB; ++i)Tb[i] = cp(B[i] & 32767, B[i] >> 15);
		for (int i = lenA; i < n; ++i)Ta[i] = cp(0, 0);
		for (int i = lenB; i < n; ++i)Tb[i] = cp(0, 0);
		DFT(Ta, n); DFT(Tb, n);
		for (int i = 0; i < n; ++i) {
			int j = (n - i) & (n - 1);
			cp A0 = (Ta[i] + conj(Ta[j])) * cp(0.5, 0);
			cp A1 = (Ta[i] - conj(Ta[j])) * cp(0, -0.5);
			cp B0 = (Tb[i] + conj(Tb[j])) * cp(0.5, 0);
			cp B1 = (Tb[i] - conj(Tb[j])) * cp(0, -0.5);
			Tc[i] = A0 * B0 + A0 * B1 * cp(0, 1);
			Td[i] = A1 * B0 + A1 * B1 * cp(0, 1);
		}
		IDFT(Tc, n); IDFT(Td, n);
		for (int i = 0; i < n; ++i) {
			ll s1 = (ll)(Tc[i].r + 0.5) % mod;
			ll s2 = (ll)(Tc[i].i + 0.5) % mod;
			ll s3 = (ll)(Td[i].r + 0.5) % mod;
			ll s4 = (ll)(Td[i].i + 0.5) % mod;
			C[i] = (s1 + ((s2 + s3) << 15) + (s4 << 30)) % mod;
		}
		return C;
	}
};

void slv(){
    int n,p;cin>>n>>p;
    vi pw(p+1),lg(p+1); int g=-1;
    auto ok=[&](int g){
        pw[0]=pw[p-1]=1;
        rep(i,1,p-2){
            pw[i]=1ll*pw[i-1]*g%p; if(pw[i]==1)return false;
        }
        rep(i,0,p-2)lg[pw[i]]=i;
        return true;
    };
    rep(i,1,p-1){
        if(ok(i)){g=i;break;}
    }
    assert(g!=-1); //p=2时g=1
    vi a(n+1),b(p-1);
    int fl=0;
    rep(i,1,n){
        cin>>a[i]; if(a[i]==0)fl=1;
    }
    if(!fl){
        cout<<"1 1\n0\n";return;
    }
    if(n==1){
        cout<<p<<" 1\n";
        rep(i,0,p-1)cout<<i<<' '; cout<<'\n';
        return;
    }
    rep(i,1,n){
        if(a[i]==0)continue;
        b[(p-1-lg[a[i]])%(p-1)]=1;
    }
    // for(auto v:b)cout<<v<<' '; cout<<'\n';
    vi ans;
    auto ck=[&](int res){
        vi c(p-1);
        rep(i,1,res)c[lg[i]]=1;
        MTT::mod=p;
        vi d=MTT::MTT(b,c);
        // cout<<res<<":\n";
        // for(auto v:b)cout<<v<<' '; cout<<'\n';
        // for(auto v:c)cout<<v<<' '; cout<<'\n';
        // for(auto v:d)cout<<v<<' '; cout<<'\n';
        ans.clear();
        rep(i,0,(int)d.size()-1){
            if(d[i]==res)ans.push_back(pw[i%(p-1)]);
        }
        return ans.size()>0;
    };
    int l=1,r=p-2;
    while(l<=r){
        int mid=l+r>>1;
        if(ck(mid))l=mid+1;
        else r=mid-1;
    }
    ck(l-1);
    sort(ans.begin(),ans.end());
    ans.resize(unique(ans.begin(),ans.end())-ans.begin());
    cout<<ans.size()<<' '<<l<<'\n';
    for(auto v:ans)cout<<v<<' '; cout<<'\n';
}
signed main(){
    IOS
    int T;cin>>T;
    while(T--)slv();
}
/*
1
3 5
0 2 3
*/

詳細信息

Test #1:

score: 100
Accepted
time: 1ms
memory: 10116kb

input:

3
2 3
0 2
3 5
2 3 4
3 5
0 2 3

output:

1 2
2 
1 1
0
2 2
2 3 

result:

ok 6 lines

Test #2:

score: -100
Wrong Answer
time: 0ms
memory: 9724kb

input:

3
1 2
0
1 2
1
2 2
1 0

output:

2 1
0 1 
1 1
0
1 1
1 

result:

wrong answer 5th lines differ - expected: '1 2', found: '1 1'