A - Phoenix and Balance
将一堆质量为2,4,8,,,2^n的硬币,分为数量相同,质量尽可能接近的两组,
2+4+8+...+2^n-1 小于 2^n(差了2),质量大的要跟质量小的在一起,所以质量差(2+2^2...2^(n/2-1))*2+2
#include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int a[100010]; int main( ) { int k,n; cin>>k; while(k--){ cin>>n; n=n/2; ll sum=0; ll a=2; while(n--){ sum+=a; a*=2; } cout<<sum<<endl; } return 0; }
B - Phoenix and Beauty
n个数,要求插入一些数,使连续的m个数和都相等,就得m个一循环,
设一共有k种数字,k>m,就不能好好循环了,k不到m个填充一些数字变成m个再循环,循环n次就肯定可以变成原来的数列啦
#include<cmath> #include<cstdio> #include<algorithm> #include<string> #include<vector> #include<iomanip> #include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int main( ) { int t; int n,k,i,sum,z; cin>>t; while(t--) { int a[10010]={0},b[10010]={0}; cin>>n>>k; sum=0; for(i=0; i<n; i++) { cin>>z; if(a[z]==0) { a[z]=1; b[sum++]=z; } } if(sum>k) { cout<<-1<<endl;; } else { cout<<n*k<<endl; for(i=sum; i<k; i++) { b[i]=1; } for(i=0; i<n; i++) { for(int j=0; j<k; j++) { cout<<b[j]<<" "; } } cout<<endl; } } return 0; }
C - Road To Zero
给两个数n,m,花费a使期中一个数-1,花费b使两个都-1,求让nm都减到0最少需要花费多少,
如果2*a<b,一个一个减就好了,如果a*2>b,min(x,y)*b+abs(x-y)*a
#include<cmath> #include<cstdio> #include<algorithm> #include<string> #include<vector> #include<iomanip> #include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int a[100010]; int main( ) { ll k,n,m,a,b,x,y; ll sum; cin>>k; while(k--){ cin>>x>>y; cin>>a>>b; if(a*2<=b){ sum=(x+y)*a; cout<<sum<<endl; }else{ sum=min(x,y)*b+abs(x-y)*a; cout<<sum<<endl; } } return 0; }
D - Binary Period
给一个字符串,只含有01,插入一些字符,使得周期最小
如果字符串中只有一种数字,就直接输出原来的字符串,周期为1
否则就输出字符串长度个数的01,周期为2最小
#include<cmath> #include<cstdio> #include<algorithm> #include<string> #include<vector> #include<iomanip> #include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int a[100010]; int main( ) { int k; int n,a,b,c,d,i; cin>>k; while(k--){ string s; cin>>s; int flag =0; for(i=1;i<s.length();i++){ if(s[i]!=s[i-1]){ flag=1; break; } } if(flag==0) { cout<<s<<endl; } else { for(i=0; i<s.length(); i++) { cout<<"01"; } cout<<endl; } } return 0; }
E - Nastya and Rice
b个再[a-b,a+b]范围内的数,总和在[c-d,c+d],问给定的数能否满足这个条件
即满足(a-b)*n<(c+d)和(a+b)*n>(c-d)
#include<cmath> #include<cstdio> #include<algorithm> #include<string> #include<vector> #include<iomanip> #include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int a[100010]; int main( ) { int k; int n,a,b,c,d; cin>>k; while(k--){ cin>>n>>a>>b>>c>>d; if((a-b)*n>(c+d)||(a+b)*n<(c-d)){ cout<<"NO"<<endl; }else{ cout<<"YES"<<endl; } } return 0; }
F - Nastya and Door
一个巨大的门,掉到山峰(比左边右边都高)上就跌成两半,给定门的长度和一串山脉,问最多能跌成几块
是前缀和!循环一圈找最大的数量
#include<cmath> #include<cstdio> #include<algorithm> #include<string> #include<vector> #include<iomanip> #include<iostream> using namespace std; typedef long long ll; #define ture true #define flase false int main( ) { int t; int n,k,i,sum,a[200100]; cin>>t; while(t--) { int b[200100]={0}; cin>>n>>k; for(i=1;i<=n;i++){ cin>>a[i]; } for(i=2;i<n;i++){ if(a[i]>a[i-1]&&a[i]>a[i+1]){ b[i]=b[i-1]+1; }else{ b[i]=b[i-1]; } } int max=0,num,flag; for(i=1;i<=n-k+1;i++){ num=b[i+k-2]-b[i]+1; if(num>max) max=num,flag=i; } cout<<max<<" "<<flag<<endl; } return 0; }