8.23<1>题解

T1

考场上全程盯着PDF,不知道OJ上有样例解释?最后题都没读懂,看到OJ上的样例解释之后恍然大悟,然后就过了,我×××××,下次我一定PDF和OJ题面都认真阅读

读懂题之后其实很简单,给序列排序,去重,然后在排好序的数组中寻找原序列前一位和后一位,看是否满足条件就可以了

 1 #include<algorithm>
 2 #include<iostream>
 3 #include<cstdio>
 4 #define int long long
 5 #define maxn 10010
 6 #define mod 2147483647
 7 using namespace std;
 8 int n,ans,ca;
 9 int a[maxn],lsh[maxn];
10 signed main()
11 {
12     while(scanf("%lld",&n)==1)
13     {
14         ca++;  ans=0;
15         for(int i=1;i<=n;++i)  {scanf("%lld",&a[i]);  lsh[i]=a[i];}
16         sort(lsh+1,lsh+n+1);
17         int len=unique(lsh+1,lsh+n+1)-lsh-1;
18         if(len==1)  {printf("Case #%lld: -1\n",ca);  continue;}
19         for(int i=1;i<=n;++i)
20         {
21             a[i]=lower_bound(lsh+1,lsh+len+1,a[i])-lsh;
22             int wz1=a[i]-1,wz2=a[i]+1;
23             if(wz1==0)  wz1=n;
24             if(wz2==len+1)  wz2=1;
25             if((lsh[wz1]+lsh[a[i]])%mod==lsh[wz2])  ans++;
26         }
27         printf("Case #%lld: %lld\n",ca,ans);
28     }
29     return 0;
30 }
View Code

T2

据说很像约瑟夫问题2?为什么人家可以打表找规律,我就找不到什么关系,好吧因为我菜,考虑一下,为了方便我们把原本$[1,n]$的编号变为$[0,n)$,每轮游戏之后都重新编号,那么第$i$轮游戏之后所有人的编号应该是向前移动了$i$,也就是变小了$i$,理解一下,原本的编号为$i$的人,编号变成了$0$,所以统一变小了$i$,那么我们就可以利用这个关系,对编号进行逆推,假设我们知道在第$i+1$轮,这个人的编号为$x$,那么在第$i$轮,此人的编号应该是$(x+i){\%}(n-(i-1))$,${\%}$的那部分是在进行第$i$轮游戏是还有多少人,这样的话$O(n)$逆推回来就可以了,记得最后给答案+1,因为我们统一把答案变小了1

 1 #include<cstdio>
 2 using namespace std;
 3 int t,n,ans;
 4 int main()
 5 {
 6     scanf("%d",&t);
 7     while(t--)
 8     {
 9         scanf("%d",&n);  ans=0;
10         for(int i=n-1;i>=1;--i)  ans=(ans+i)%(n-i+1);
11         printf("%d\n",ans+1);
12     }
13     return 0;
14 }
View Code

T3

其实就是一个裸的求解数学式子,那我们就先把它抽象为求$N^a{\%}p$而问题出现在了他给的模数$p$不是质数,我们发现$p=2{\times}p_1$,那我们可以把$N^a$分别对2和$p_1$取模,然后合并$CRT$,对$2$取模很简单,只需要判一下$N$的奇偶就可以得到答案,对于另一个式子$N^a{\%}p_1$,由于$a$是组合数的加和,可能会爆$long long$,所以根据某定理,该式可变为$N^{a{\%}{\varphi}(p_1)}{\%}p_1$,那又有一个新问题出现了,$p_1$是质数然而${\varphi}(P_1)$也就是$p_1-1$不为质数,要怎么求呢?分解质因数,求在模每个质因数意义下的$a$的值,还是合并$CRT$即可,这不就××是道$CRT$的板子题嘛,我不会能怎么办

 1 //求N^(a%phi(mod))%phi(mod)
 2 //phi(mod)分解质因数,求对每个数取模意义下的组合数,求出模每个数意义下的C之和,之后合并CRT
 3 //给合并CRT之后的结果直接快速幂求结果
 4 //再把结果和1或0CRT一下就可以了
 5 #include<iostream>
 6 #include<cstdio>
 7 #include<vector>
 8 #define ll long long
 9 #define moddd 54184622
10 #define maxn 1001000
11 using namespace std;
12 int n,g;
13 int mod[6]={0,2,3,5,7,129011};
14 ll jc[maxn],ny[maxn];
15 vector <int> G;
16 vector <ll> ans;
17 int gcd(int a,int b)
18 {
19     return (b==0)?a:gcd(b,a%b);
20 }
21 ll ksm(ll a,ll b,ll c)
22 {
23     ll ans=1;
24     while(b)
25     {
26         if(b&1)  ans=(ans*a)%c;
27         a=(a*a)%c;  b=b>>1;
28     }
29     return ans;
30 }
31 ll C(int n,int m,int modd)
32 {
33     if(n<m)  return 0;
34     if(n<modd&&m<modd)  return ((jc[n]*ny[m])%modd*ny[n-m])%modd;
35     return (C(n/modd,m/modd,modd)*C(n%modd,m%modd,modd))%modd;
36 }
37 ll exgcd(ll a,ll b,ll &x,ll &y)
38 {
39     if(b==0)  {x=1;  y=0;  return a;}
40     int gcd=exgcd(b,a%b,x,y);
41     int t=x;  x=y;  y=t-a/b*y;
42     return gcd;
43 }
44 ll CRT()
45 {
46     ll x,y;  ll a=0,mm,nn=1;
47     for(int i=1;i<=5;++i)  nn*=mod[i];
48     for(int i=1;i<=5;++i)
49     {
50         mm=nn/mod[i];
51         exgcd(mod[i],mm,x,y);
52         a=(a+y*mm*ans[i-1])%nn;
53     }
54     if(a>0)  return a;
55     else  return a+nn;
56 }
57 ll CRTT(ll xxx)
58 {
59     ll x,y;  ll a=0,mm,nn=moddd;
60     mm=nn/2;  exgcd(2,mm,x,y);  a=(a+y*mm*(n%2))%nn;
61     mm=2;  exgcd(moddd/2,mm,x,y);  a=(a+y*mm*xxx)%nn;
62     if(a>0)  return a;
63     else  return a+nn;
64 }
65 int main()
66 {
67     scanf("%d%d",&n,&g);
68     for(int i=1;i<=n;++i)
69         if(gcd(i,n)==1)  G.push_back(i);
70     for(int i=1;i<=5;++i)
71     {
72         int p=mod[i],minnn=min(g,p-1);  jc[0]=1;  
73         for(int i=1;i<=minnn;++i)  jc[i]=(jc[i-1]*i)%p;
74         ny[minnn]=ksm(jc[minnn],p-2,p);
75         for(int i=minnn;i>=1;--i)  ny[i-1]=(ny[i]*i)%p;
76         ll an=0;
77         for(int i=0;i<G.size();++i)  an+=C(g,G[i],p);
78         ans.push_back(an);
79     }
80     ll tot=ksm(n,CRT(),moddd/2);
81     printf("%lld\n",CRTT(tot));
82     return 0;
83 }
View Code

 

posted @ 2019-08-23 17:27  hzoi_X&R  阅读(134)  评论(0编辑  收藏  举报