codeforces 794G. Replace All
来源:互联网 发布:ubuntu 传输文件 编辑:程序博客网 时间:2024/05/19 16:03
题目大意:给两个'A''B''?'组成的串XY,'?'可以是'A'或'B',求所有'?'的情况下,将'A''B'换成两个长度小于n的01串的方案数和。
这好像有一些奥妙重重的性质。
先考虑一个简单的情况:第一个串有a个'A',第二个串有b个'B'。设'A'=>A,'B'=>B。b*|A|=a*|B|,且AB串coprime(是官方题解中的说法,互质,就像辗转相除法一样的感觉)。由于这样的性质,不妨设B=AX,X是一个串。存在AB=BA。
如果AB互质,"AB"="BA",对任何询问都能转换"A..AB..B","A..AB..B"。如果这两个串不同,等价于上面情况,可以直接做,否则即要统计互质的AB串对数,使用容斥解决。
但是如果AB不互质,刚才的方法还是无法解决(此处强调AB是求出来的答案01串)。经过分析,X!=Y时,AB互质,证明略;X==Y时,A==B,容易计算。
至此问题已解决,复杂度O(nlogn+len)。
#include<bits/stdc++.h>#define P 1000000007#define N 600005#define ll long longusing namespace std;int l1,l2,n,Aa,Ba,Ca,Ab,Bb,Cb,flag,CC;ll ans,inv[N],sum[N],po[N],fac[N],ifac[N],G;char a[N],b[N];int gcd(int x,int y){return y?gcd(y,x%y):x;}ll C(int x,int y){return fac[y]*ifac[y-x]%P*ifac[x]%P;}int main(){scanf("%s%s",a+1,b+1);l1=strlen(a+1);l2=strlen(b+1);scanf("%d",&n);/**/po[0]=1;for (int i=1;i<=600000;i++)po[i]=po[i-1]*2%P;inv[1]=1;for (int i=2;i<=600000;i++)inv[i]=(-P/i)*inv[P%i]%P;fac[0]=1;ifac[0]=1;for (int i=1;i<=600000;i++)fac[i]=fac[i-1]*i%P,ifac[i]=ifac[i-1]*inv[i]%P;flag=l1==l2;for (int i=1;i<=l1;i++){if (a[i]=='A') Aa++;if (a[i]=='B') Ba++;if (a[i]=='?') Ca++;flag&=a[i]==b[i]||a[i]=='?'||b[i]=='?';if (a[i]=='?'&&b[i]=='?') CC++;}for (int i=1;i<=l2;i++){if (b[i]=='A') Ab++;if (b[i]=='B') Bb++;if (b[i]=='?') Cb++;}//calc G 小于n的coprime串对数 gcd (n/d)^2*2^dfor (int i=1;i<=n;i++)sum[i]=(ll)(n/i)*(n/i)%P;for (int i=n;i>=1;i--){for (int j=2;j<=n/i;j++)sum[i]=(sum[i]-sum[i*j])%P;G=(G+sum[i]*po[i]%P)%P;}for (int i=-Cb;i<=Ca;i++){//a: Aa+u Ba+Ca-u//b: Ab+v Bb+Cb-v//magic//a: Aa-Ab+u-v//b: Bb+Cb-Ba-Ca-v+u//i=u-vint A=Aa-Ab+i,B=Bb+Cb-Ba-Ca+i;ll t=C(Cb+i,Ca+Cb);if ((ll)A*B<0) continue;if (A<=0&&B<=0) A=-A,B=-B;if (A==0&&B==0){//cout<<G<<endl;if (flag){ans=(ans+(po[n+1]-2)*(po[n+1]-2)%P*po[CC]%P)%P;t=(t-po[CC]+P)%P;}ans=(ans+t*G)%P;continue;}if (A>B) swap(A,B);if (A==0) continue;ans=(ans+t*(po[n/(B/gcd(A,B))+1]-2)%P)%P;//cout<<A<<' '<<B<<' '<<t<<' '<<ans<<endl;}printf("%lld\n",(ans+P)%P);}
阅读全文
1 0
- CodeForces 794G. Replace All
- codeforces 794G. Replace All
- Codeforces Round #414 (Div1+Div2) G Replace All (组合数学)
- JavaScript String Replace All
- javascript replace all
- str.replace(/[ ]/g, "");
- Codeforces Gym 100814 G It is all about wisdom 二分+最短路
- replace(/\s/g,"")中的/g是什么意思?
- JavaScript中的replace 达到replace.all函数替换的问题
- Replace all Matches (替换所有匹配)
- POJ 1936 All in All G++
- JS 字符串全部替换 ,replace (/ /g,'')
- js中 replace(/\//g, '') 什么作用.
- String.replace(/\s/g,'')中的‘/\s/g’表示什么意思?
- replace(//s/g,"")中的/g是什么意思? 及replace函数的用法
- codeforces 234G Practice
- CodeForces 589G Hiring
- codeforces 626G
- C动态分配内存
- 自学react-native之必备知识点(ES6+ReactJS+flexbox)
- Linux搭建SVN
- 常用平台包名
- 设计模式-状态模式
- codeforces 794G. Replace All
- c++ 为什么析构函数必须声明为虚函数
- ORACLE Hints
- selenium webdriver方法qiut()close()区别
- 乐视断缴社保 乐视负债百亿 钱景堪忧!
- PCB布高速线——需要考虑信号传输延时
- 获取复选框的值
- spring学习笔记一
- xml文件解析的几种方式(一)