A:Circle of Students
直接模拟
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 203; int a[maxn]; int main() { int q; scanf("%d",&q); while(q--) { int n; scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%d",&a[i]); a[n+1]=a[1]; if(n==1) { printf("YES\n");continue; } int flag=0,u=0,v=0; for(int i=2;i<=n;i++) if(a[i]-a[i-1]==1) u++; else break; for(int i=n+1;i>=2;i--) if(a[i]-a[i-1]==1) v++; else break; if(u+v==n-1) { printf("YES\n");continue; } u=v=0; for(int i=2;i<=n;i++) if(a[i]-a[i-1]==-1) u++; else break; for(int i=n+1;i>=2;i--) if(a[i]-a[i-1]==-1) v++; else break; if(u+v==n-1) { printf("YES\n");continue; } printf("NO\n"); } return 0; }
B: Equal Rectangles
分析:排序后最大乘最小等于矩形面积,判断一下即可
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 1004; int a[maxn]; map<int,int> mp; ll max(ll a,ll b){return a>b?a:b;}ll min(ll a,ll b){return a<b?a:b;} int main() { int q; scanf("%d",&q); while(q--) { int n,flag=0; mp.clear(); scanf("%d",&n); for(int i=1;i<=n*4;i++) { scanf("%d",&a[i]); mp[a[i]]++; } map<int,int>::iterator it = mp.begin(); for(;it!=mp.end();it++) if(((*it).second)%2==1) { flag=1;break; } if(flag) { printf("NO\n"); continue; } sort(a+1,a+1+n*4); int l=1,r=n*4,s=a[1]*a[4*n]; while(l<r) { if(a[l]*a[r]!=s) { flag=1;break; } l++;r--; } if(flag) printf("NO\n"); else printf("YES\n"); } return 0; }C: Common Divisors
分析: 求数列gcd后算gcd的因子数量
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; ll GCD(ll a,ll b) { if(b==0) return a;else if(a==0) return b; return a%b==0?b:GCD(b,a%b); } int main() { int n; ll x,gcd=0,ans=0; scanf("%d",&n); for(int i=1;i<=n;i++) { scanf("%I64d",&x); gcd=GCD(x,gcd); } for(ll i=1;i*i<=gcd;i++) { if(gcd%i==0&&i*i!=gcd) ans+=2; else if(gcd%i==0&&i*i==gcd)ans++; } printf("%I64d",ans); return 0; }
D1:Remove the Substring (easy version)
分析:数据很小,直接枚举要删除的substring
代码:
分析:三种情况,(1)删除最左端一段(2)删除最右端一端(3)删除中间某一段。O(n)复杂度算出两个数组,l[maxn] 和 r[maxn],l[i]表示从s[0]到s[|s|-1]遍历t[i]最早出现的位置(即尽量靠左),r[i]表示从s[|s|-1]到s[0]遍历t[i]最早出现的位置(即尽量靠右)。对于(1),ans=r[0],对于(2),ans=|s| - l[|t| - 1]-1,对于(3),ans=max(r[i] - l[i-1] -1) { 1<=i<=|t|-1 }。取三种情况最大的
#include <bits/stdc++.h> using namespace std; typedef long long ll; int main() { string s,t; cin>>s>>t; int ans=0; for(int i=0;i<s.length();i++) for(int j=i;j<s.length();j++) { int now=0; for(int k=0;k<s.length();k++) if(k>=i&&k<=j) continue; else if(t[now]==s[k]) { now++; if(now==t.length()) break; } if(now==t.length()) ans=max(ans,j-i+1); } cout<<ans; return 0; }D2:Remove the Substring (hard version)
分析:三种情况,(1)删除最左端一段(2)删除最右端一端(3)删除中间某一段。O(n)复杂度算出两个数组,l[maxn] 和 r[maxn],l[i]表示从s[0]到s[|s|-1]遍历t[i]最早出现的位置(即尽量靠左),r[i]表示从s[|s|-1]到s[0]遍历t[i]最早出现的位置(即尽量靠右)。对于(1),ans=r[0],对于(2),ans=|s| - l[|t| - 1]-1,对于(3),ans=max(r[i] - l[i-1] -1) { 1<=i<=|t|-1 }。取三种情况最大的
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 2e5 + 3; int l[maxn],r[maxn]; int main() { string s,t; cin>>s>>t; int ans=0; for(int i=0,j=0;i<s.length()&&j<t.length();i++) if(s[i]==t[j]) l[j++]=i; for(int i=s.length()-1,j=t.length()-1;i>=0&&j>=0;i--) if(s[i]==t[j]) r[j--]=i; ans=max(r[0],int(s.length()-l[t.length()-1]-1)); for(int i=1;i<s.length();i++) ans=max(ans,r[i]-l[i-1]-1); cout<<ans; return 0; }
E: Boxers
分析:排序后用桶装一下
分析:排序后用桶装一下
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 2e5 + 2; int a[maxn],c[maxn]; int main() { int n; scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%d",&a[i]); sort(a+1,a+1+n); for(int i=1;i<=n;i++) { if(a[i]-1==0) { if(!c[a[i]]) c[a[i]]=1; else c[a[i]+1]=1; } else{ if(!c[a[i]-1]) c[a[i]-1]=1; else if(!c[a[i]]) c[a[i]]=1; else c[a[i]+1]=1; } } int ans=0; for(int i=1;i<=150001;i++) if(c[i]) ans++; printf("%d",ans); return 0; }F1. Complete the Projects (easy version)
分析: 贪心排序后check一遍 (详见tutorial:https://codeforces.com/blog/entry/69108)
代码:
分析: 贪心排序后背包 (详见tutorial:https://codeforces.com/blog/entry/69108)
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 104; struct node { ll a,b; }; vector<node> c,neg; bool cmp(const node &A,const node &B) { return (A.a+A.b)>(B.a+B.b); } bool cmp2(const node &A,const node &B) { return A.a<B.a; } int main() { int n; ll r,x,y; scanf("%d%I64d",&n,&r); for(int i=1;i<=n;i++) { scanf("%I64d%I64d",&x,&y); if(y>=0) c.push_back({x,y}); else neg.push_back({max(x,-y),y}); } sort(c.begin(),c.end(),cmp2); sort(neg.begin(),neg.end(),cmp); for(int i=0;i<c.size();i++) if(r<c[i].a) { printf("NO"); return 0; } else r+=c[i].b; for(int i=0;i<neg.size();i++) if(r<neg[i].a) { printf("NO"); return 0; } else r+=neg[i].b; printf("YES"); return 0; }F2. Complete the Projects (hard version)
分析: 贪心排序后背包 (详见tutorial:https://codeforces.com/blog/entry/69108)
代码:
#include <bits/stdc++.h> using namespace std; typedef long long ll; const int maxn = 60004; struct node { ll a,b; }; vector<node> c,neg; int dp[maxn]; bool cmp(const node &A,const node &B) { return A.a<B.a; } bool _cmp(const node &A,const node &B) { return (A.a+A.b)<(B.a+B.b); } int main() { int n,ans=0; ll r,x,y; cin>>n>>r; for(int i=1;i<=n;i++) { cin>>x>>y; if(y>=0) c.push_back({x,y}); else neg.push_back({max(x,-y),y}); } sort(c.begin(),c.end(),cmp); sort(neg.begin(),neg.end(),_cmp); for(int i=0;i<c.size();i++) if(r<c[i].a) break; else { r+=c[i].b; ans++; } for(int i=0;i<neg.size();i++) for(ll j=r;j>=abs(neg[i].b);j--) if(j>=neg[i].a&&j+neg[i].b>=0) dp[j]=max(dp[j],dp[j+neg[i].b]+1); ans+=dp[r]; cout<<ans; return 0; }