A. Odd Divisor
奇数是没有2的因子,那么我们将他反复除2即可.
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int N=2e5+50; int w[N]; int main() { int T; //T=1; cin>>T; while(T--) { ll n; cin>>n; if(n%2==0) while(n%2==0) n/=2; if(n>1) puts("YES"); else puts("NO"); } return 0; }
New Year's Number
2020*2020大于1e6了,我们将n/2020.看需要分配多少个1即可.
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int N=2e5+50; int w[N]; int main() { int T; //T=1; cin>>T; while(T--) { ll n; cin>>n; int cnt=n/2020; if(cnt>=n%2020) puts("YES"); else puts("NO"); } return 0; }
C. Ball in Berland
考虑方案数=总的-一组相同的+两组相同的.
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int N=2e5+5; ll a[N],b[N]; ll C(ll A,ll B) { return A*(A-1)/2ll; } map<int,int>s1; map<int,int>s2; map<pair<int,int>,int>s3; int main() { int T; cin>>T; while(T--) { s1.clear(); s2.clear(); s3.clear(); ll A,B,n; scanf("%lld%lld%lld",&A,&B,&n); ll ans=C(n,2); for(int i=1;i<=n;i++) scanf("%lld",&a[i]); for(int i=1;i<=n;i++) scanf("%lld",&b[i]); for(int i=1;i<=n;i++) { s1[a[i]]++;s2[b[i]]++; s3[{a[i],b[i]}]++; }//cout<<ans<<endl; for(auto x:s1) if(x.second>1) ans-=C(x.second,2); for(auto x:s2) if(x.second>1) ans-=C(x.second,2); for(auto x:s3) if(x.second>1) ans+=C(x.second,2); printf("%lld\n",ans); } return 0; }
D. Cleaning the Phone
发现bi<=2.那么分bi=1和bi=2贪心讨论即可.注意别取两个bi=1的,会增加讨论难度.
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int mod=1e9+7; const int N=2e5+5; struct node{ int a,b; }w[N]; bool cmp(node A,node B) { if(A.b==B.b) return A.a>B.a; else return A.b<B.b; } ll qp(ll a,ll b) { ll res=1; while(b) { if(b&1) res=res*a%mod; a=a*a%mod; b>>=1; }return res; } ll f[N],ivf[N]; void init() { f[0]=1; for(ll i=1;i<=N-5;i++) f[i]=f[i-1]*i%mod; ivf[N-5]=qp(f[N-5],mod-2); for(ll i=N-5;i>=1;i--) ivf[i-1]=ivf[i]*i%mod; } ll C(ll a,ll b) { return f[a]*ivf[b]%mod*ivf[a-b]%mod; } int main() { int T; init(); cin>>T; while(T--) { int n,m;scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) scanf("%d",&w[i].a); for(int i=1;i<=n;i++) scanf("%d",&w[i].b); sort(w+1,w+1+n,cmp);int pos=n+1; for(int i=1;i<=n;i++) { if(w[i].b==2) { pos=i;break; } }bool f=false;int ans=0,num=0; int cnt=0;int l=1,r=pos; while(!f&&cnt<n) { if(pos-l>1) { if(r>n) num+=w[l].a,l++,cnt++,ans++; else if(w[l].a+num>=m) num+=w[l].a,l++,cnt++,ans++; //else if(r<=n&&w[l].a+w[l+1].a+num<m&&w[r].a+w[l].a>=m) num+=w[l].a+w[r].a,l++,r++,cnt+=2,ans+=3; else if(w[l].a+w[l+1].a>w[r].a) num+=w[l].a,l++,cnt++,ans++; else num+=w[r].a,r++,cnt++,ans+=2; } else { if(r>n) num+=w[l].a,l++,cnt++,ans++; else { if(num+w[l].a>=m&&l!=pos) num+=w[l].a,l++,cnt++,ans++; else num+=w[r].a,r++,cnt++,ans+=2; } }if(num>=m) f=true; //cout<<num<<endl; } if(f) cout<<ans<<'\n'; else puts("-1"); } return 0; } /* 1 4 10 5 1 3 4 1 2 1 2 */
E.Advertising Agency
大的一定要取,边界溢出的组合数取一下即可.
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int mod=1e9+7; const int N=1e3+5; ll a[N]; ll qp(ll a,ll b) { ll res=1; while(b) { if(b&1) res=res*a%mod; a=a*a%mod; b>>=1; }return res; } ll f[N],ivf[N]; void init() { f[0]=1; for(ll i=1;i<=N-5;i++) f[i]=f[i-1]*i%mod; ivf[N-5]=qp(f[N-5],mod-2); for(ll i=N-5;i>=1;i--) ivf[i-1]=ivf[i]*i%mod; } ll C(ll a,ll b) { return f[a]*ivf[b]%mod*ivf[a-b]%mod; } int main() { int T; init(); cin>>T; while(T--) { ll n,k;cin>>n>>k; map<int,int>p;p.clear(); for(int i=1;i<=n;i++) scanf("%lld",&a[i]); sort(a+1,a+1+n);ll num=0;ll tot=0; for(int i=n-k;a[i]>=a[n-k+1];i--) num++; tot=num;//cout<<tot<<endl; for(int i=n-k+1;a[i]<=a[n-k+1]&&i<=n;i++) tot++; cout<<C(tot,num)<<'\n'; } return 0; }
F.Unusual Matrix
每个操作只会用一次.瞎搞即可.
#include <bits/stdc++.h> using namespace std; const int N=1e3+50; char s[N][N]; char p[N][N]; bool h[N];//观察这行用了没. bool l[N];//观察这列用了没. int main() { int T;scanf("%d",&T); while(T--) { int n;scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%s",s[i]+1); for(int i=1;i<=n;i++) scanf("%s",p[i]+1); for(int i=1;i<=n;i++) h[i]=l[i]=false; bool flag=true; for(int i=1;i<=n;i++) { int cnt=0; for(int j=1;j<=n;j++) { if(i==1)//动列. { if(s[i][j]!=p[i][j]) l[j]=true; } else { if(s[i][j]!=p[i][j]&&l[j]==false) cnt++; else if(s[i][j]==p[i][j]&&l[j]==true) cnt++; } }if(cnt!=0&&cnt!=n) flag=false; } if(flag) puts("YES"); else puts("NO"); } return 0; }
G.Strange Beauty
集合一定是相互之间成倍数的,然后直接简单dp一下即可,可以预先处理出来因子.
#include <bits/stdc++.h> using namespace std; const int N=2e5+5; int a[N]; vector<int>v[N]; void init() { for(int i=1;i<=2e5;i++) { for(int j=i;j<=2e5;j+=i) { v[j].push_back(i); } } } int main() { int T;scanf("%d",&T); init(); while(T--) { unordered_map<int,int>p,f; int n;scanf("%d",&n); for(int i=1;i<=n;i++) { scanf("%d",&a[i]);p[a[i]]++; }int ans=0;sort(a+1,a+1+n); int cnt=unique(a+1,a+1+n)-a-1; for(int i=1;i<=cnt;i++) { f[a[i]]=p[a[i]]; for(int j:v[a[i]]) { if(a[i]!=j) f[a[i]]=max(f[a[i]],f[j]+p[a[i]]); //if(j!=a[i]/j&&j!=1) if[a[i]]=max(f[a[i]],f[a[i]/j]+p[a[i]]); }ans=max(f[a[i]],ans); }//for(int i=1;i<=4;i++) cout<<f[a[i]]<<endl; printf("%d\n",n-ans); } return 0; }