昨天也是理完发赶回来打的这场比赛,可惜头发剪毁了,但是打的还不错,算是因祸得福(?
这是我第一次在八千多人参赛的情况下获得137名的成绩,虽然不是特别好,但是对我来说很开心了
A题

很简单的思想,移项得到差分数组,维护并更新答案就可以
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| #include <iostream> using namespace std; using ll=long long; const int N=1e5+20; ll a[N],d[N]; int main() { ll n;cin>>n; for(ll i=1;i<=n;i++){ cin>>a[i]; d[i]=a[i]-a[i-1]; } ll ans=0; for(int i=2;i<=n-1;i++){ if((a[i+1]<=d[i]))ans++; } cout<<ans; return 0; }
|
B题

这道题很简单,一个贪心的思想,尽量在最高位放大的数字,最多只能放9,多余的放在次高位,以此类推
需要注意的是,给的m是有可能大于你最多能表示的数字的,因为要求是f(x)<=M,所以要在9*n和m里取min
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| #include <iostream> #include<string.h> #include<cmath> using namespace std; using i64=long long; int main() { i64 n,m; cin>>n>>m; string s=""; m=min(m,n*9); while(m>=10){ s+=to_string(9); m-=9; } s+=to_string(m); while(s.size()<n){ s+="0"; } cout<<s; return 0; }
|
C题

一道升级的最大字段和,那我们可以预处理一下,一个线性筛求出所有质数,再以所有质数为子数组的长度取答案,取的时候可以利用一个前缀和做到O(1)的查询。需要注意的是在预处理质数的时候N最好开大一点,因为线性筛的特性有时会导致一些合数没有被筛掉
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37
| #include <iostream> #include<cstring> #include<algorithm> #include<cmath> #include<vector> using namespace std; const int N=2e5+10; using i64=long long; vector<int>prime; bool vis[N]; i64 a[N],pre[N]; int main() { memset(vis,1,sizeof vis); i64 n;cin>>n; for(int i=2;i<=n;i++){ if(vis[i])prime.push_back(i); for(int j=0;j<prime.size()&&i*prime[j]<=N;j++){ vis[i*prime[j]]=0; if(i%prime[j]==0)break; } } for(int i=1;i<=n;i++){ cin>>a[i]; pre[i]=pre[i-1]+a[i]; } i64 ans=-0x3f3f3f3f; for(auto &e:prime){ if(e>n)break; for(i64 i=1;(i+e-1)<=n;i++){ ans=max(ans,pre[i+e-1]-pre[i-1]); } } cout<<ans; return 0; }
|