标签:全排列 splay || const algo %s 查找 sizeof dff
B.http://codeforces.com/contest/584/problem/B
题意:给出3n个点,每个点有个值a[i](大小为[1,3]),当一个序列中至少存在一个i,满足a[i]+a[i+n]+a[i+2*n]!=6则该序列满足条件,求有多少序列满足条件
分析:组合数学。因为条件为“至少”,所以去求反面,即总排列-没有一个i满足条件。将3个点看作一组,对于i,i+n,i+2*n来说全排列为27,而当a[i]+a[i+n]+a[i+2*n]==6时,有7组。那么对于3n来说得到公式ans=27^n-7^n,用快速幂进行处理即可
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<cmath> 5 using namespace std; 6 typedef long long ll; 7 const ll mod=1e9+7; 8 9 ll pow_(ll x,ll k) 10 { 11 ll ans=1; 12 while ( k ) 13 { 14 if ( k&1 ) ans=(ans*x)%mod; 15 x=(x*x)%mod; 16 k/=2; 17 } 18 return ans; 19 } 20 21 int main() 22 { 23 ll n,i,j,k,ans; 24 while ( scanf("%lld",&n)!=EOF ) 25 { 26 ans=((pow_(3,3*n)-pow_(7,n))%mod+mod)%mod; 27 printf("%lld\n",ans); 28 } 29 return 0; 30 }
C.http://codeforces.com/contest/584/problem/C
题意:给定两个字符串s1,s2,长度为n,先定义函数f(a,b)表示两个长度相同的字符串a,b对应位置字符不同的个数。现在让你构造一个字符s3,满足f(s1,s3)=f(s2,s3)=t。
分析:设left=n-t表示s3与s1,s2有多少个位置的字符相同,构造字符相同的位置时首先考虑s1和s2本身就字符就已经相同的位置(数量记为t_)。
记cnt1,cnt2分别为s1,s2中需要和s3字符相同位置的数量,然后再从头开始,先构造与s1相同的位置,再构造与s2相同的位置,最后构造与s1,s2都不同的位置(构造方法是初始now=‘a‘,当与s1或者s2相同时,now++,直至与s1,s2对应位置都不相同为止,s3[i]=now)
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 using namespace std; 5 const int maxn=1e5+10; 6 char s1[maxn],s2[maxn],s3[maxn]; 7 bool vis[maxn]; 8 9 int main() 10 { 11 int n,t,i,j,k,x,y,z,t_,cnt1,cnt2,now,left; 12 while ( scanf("%d%d",&n,&t)!=EOF ) 13 { 14 scanf("%s%s",s1,s2); 15 memset(vis,false,sizeof(vis)); 16 t_=0; 17 left=n-t; 18 for ( i=0;i<n;i++ ) 19 { 20 if ( s1[i]==s2[i] ) 21 { 22 t_++; 23 if ( left>0 ) 24 { 25 vis[i]=true; 26 s3[i]=s1[i]; 27 left--; 28 } 29 } 30 } 31 if ( n-2*t-t_>0 ) 32 { 33 printf("-1\n"); 34 continue; 35 } 36 cnt1=cnt2=left; 37 for ( i=0;i<n;i++ ) 38 { 39 if ( !vis[i]) 40 { 41 if ( cnt1!=0 && s1[i]!=s2[i] ) 42 { 43 vis[i]=true; 44 s3[i]=s1[i]; 45 cnt1--; 46 } 47 else 48 { 49 if ( cnt2!=0 && s1[i]!=s2[i] ) 50 { 51 vis[i]=true; 52 s3[i]=s2[i]; 53 cnt2--; 54 } 55 else 56 { 57 now=‘a‘; 58 while ( now==s1[i] || now==s2[i] ) now++; 59 s3[i]=now; 60 vis[i]=true; 61 } 62 } 63 } 64 } 65 printf("%s\n",s3); 66 } 67 return 0; 68 }
D.http://codeforces.com/contest/584/problem/D
题意:给出一个奇数,问是否存在(1个/2个/3个)质数,使得这几个质数之和为这个奇数
分析:思路1:根据哥德巴赫猜想,一个大于2的偶数可以分解成两个素数. 所有我们将其中的一个奇数定为3,剩下的就是值就变成一个偶数,通过暴力查找
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<cmath> 5 using namespace std; 6 7 bool isprime(int x) 8 { 9 for ( int i=2;i<=sqrt(x);i++ ) 10 { 11 if ( x%i==0 ) return false; 12 } 13 return true; 14 } 15 16 int main() 17 { 18 int n,i,j,k,ans,cnt,num; 19 while ( scanf("%d",&n)!=EOF ) 20 { 21 if ( isprime(n) ) printf("1\n%d\n",n); 22 else { 23 n-=3; 24 printf("3\n3"); 25 for ( i=2;i<=n;i++ ) 26 { 27 if ( isprime(i) && isprime(n-i) ) 28 { 29 printf(" %d %d\n",i,n-i); 30 break; 31 } 32 } 33 } 34 } 35 return 0; 36 }
思路2:具体见https://blog.csdn.net/aaaaacmer/article/details/49448021 大致就是根据分成几个数的和+奇偶性来确定最后的值
1 #include<cstdio> 2 #include<cstring> 3 #include<algorithm> 4 #include<cmath> 5 using namespace std; 6 7 bool isprime(int x) 8 { 9 for ( int i=2;i<=sqrt(x);i++ ) 10 { 11 if ( x%i==0 ) return false; 12 } 13 return true; 14 } 15 16 int main() 17 { 18 int n,ans,a,b,c,i,j,k; 19 bool flag; 20 while ( scanf("%d",&n)!=EOF ) 21 { 22 if ( isprime(n) ) 23 { 24 printf("1\n%d\n",n); 25 continue; 26 } 27 if ( isprime(n-2) ) 28 { 29 printf("2\n2 %d\n",n-2); 30 continue; 31 } 32 if ( isprime(n-4) ) 33 { 34 printf("3\n2 2 %d\n",n-4); 35 continue; 36 } 37 flag=false; 38 for ( i=n-6;i>=3;i-- ) 39 { 40 if ( isprime(i) ) 41 { 42 for ( j=n-i-3;j>=3;j-- ) 43 { 44 if ( isprime(j) ) 45 { 46 k=n-i-j; 47 if ( isprime(k) ) 48 { 49 flag=true; 50 printf("3\n%d %d %d\n",k,i,j); 51 break; 52 } 53 } 54 } 55 if ( flag ) break; 56 } 57 } 58 } 59 return 0; 60 }
Codeforces Round #324 (Div. 2)
标签:全排列 splay || const algo %s 查找 sizeof dff
原文地址:https://www.cnblogs.com/HDUjackyan/p/9066407.html