不可发送单个标点符号 | 题解:P9164 「INOH」Round 1 - 狂气
Petit_Souris · · 题解
看起来就不是什么正常思路的 DS 题,结合模数
设奇数位的生成函数为
那么操作
考虑做一个类似半在线卷积的分治 NTT:对于一个分治区间
取中点
除去模板的关键代码:
using namespace Poly;
ll n;
char s[N];
array<poly,4> solve(ll l,ll r){
if(l==r){
array<poly,4> ret;
if(s[l]=='1'){
ret[0].resize(1),ret[1].resize(1),ret[2].resize(1),ret[3].resize(1);
ret[0][0]=1,ret[2][0]=1,ret[3][0]=1;
}
else {
ret[0].resize(1),ret[1].resize(2),ret[2].resize(1),ret[3].resize(1);
ret[0][0]=1,ret[1][1]=1,ret[3][0]=1;
}
return ret;
}
ll mid=(l+r)>>1;
array<poly,4>L=solve(l,mid),R=solve(mid+1,r),ret;
ret[0]=R[0]*L[0]+R[1]*L[2];
ret[1]=R[0]*L[1]+R[1]*L[3];
ret[2]=R[2]*L[0]+R[3]*L[2];
ret[3]=R[2]*L[1]+R[3]*L[3];
return ret;
}
bool Med;
int main(){
cerr<<fabs(&Med-&Mbe)/1048576.0<<"MB\n";
n=read();
scanf("%s",s+1);
array<poly,4> ret=solve(1,n);
ll ans=1,pos=1;
for(ll x:ret[0].a){
if(pos>n)break;
ans=1ll*ans*(x+1)%Mod,pos+=2;
}
pos=2;
for(ll x:ret[2].a){
if(pos>n)break;
ans=1ll*ans*(x+1)%Mod,pos+=2;
}
write(ans);
cerr<<"\n"<<clock()*1.0/CLOCKS_PER_SEC*1000<<"ms\n";
return 0;
}