涵盖知识点:DP、图论etc.
比赛链接:
https://codeforces.com/contest/1307
A:Cow and Haybales
题意:每一步可以将第n个数字-1,第n-1个数字+1.给你d步问你第1个数字最大能变为多少。
题解:贪心、模拟。一个一个扫描判断步数是否足够。
AC代码:
1 //A 2 #include3 using namespace std; 4 int num[110]; 5 int main(){ 6 int t; 7 cin>>t; 8 while(t--){ 9 int n,d; 10 cin>>n>>d; 11 for(int i=0;i ){ 12 cin>>num[i]; 13 } 14 int res=num[0]; 15 for(int i=1;i ){ 16 if(num[i]*i<=d){ 17 res+=num[i]; 18 d-=num[i]*i; 19 }else{ 20 res+=d/i; 21 break; 22 } 23 } 24 cout< "\n"; 25 } 26 return 0; 27 }
B:Cow and Friend
题意:在2D平面内要求从(0,0)跳到(x,0)。每次跳的距离需要满足给定的n个具体数值。问最少条几次可以满足条件。
题解:如果x在所给定的n个数值中,那么只需要一步。否则,设n个数值内最大值为m,最终所求的答案ans=max(2,ceil(x/m)).证明:1.至少两步。2.前ans-2步沿着x轴跳动m(ans-2)的距离,第ans-1步总存在一个方向使得最后一步的起点和终点之间的距离在n个数之内。
AC代码:
1 //B 2 #include3 using namespace std; 4 set<int> s; 5 6 int main(){ 7 int t; 8 cin>>t; 9 while(t--){ 10 s.clear(); 11 int n,x; 12 cin>>n>>x; 13 int ma=0; 14 while(n--){ 15 int a; 16 cin>>a; 17 s.insert(a); 18 ma=max(a,ma); 19 } 20 if(s.count(x)){ 21 cout<<"1\n"; 22 }else{ 23 cout< 2,(x+ma-1)/ma)<<"\n"; 24 } 25 } 26 return 0; 27 }
C:Cow and Message
题意:在一个字符串中下标满足等差数列的子序列当中找出出现次数最多的那个子序列。
题解:如果子序列长度大于2,那么一个长度为2或者长度为1的子序列必定同时满足条件。所以只考虑长度为1的和长度为2的子序列。长度为1的扫描一遍,长度为2的dp一下即可。
AC代码:
1 //C 2 #include3 using namespace std; 4 const int maxn=26; 5 typedef long long ll; 6 ll cnt[maxn],dp[maxn][maxn]; 7 int main(){ 8 string s; 9 cin>>s; 10 for(int i=0;i ){ 11 for(int j=0;j ){ 12 dp[j][s[i]-'a']+=cnt[j]; 13 } 14 cnt[s[i]-'a']++; 15 } 16 ll res=0; 17 for(int i=0;i ){ 18 res=max(res,cnt[i]); 19 for(int j=0;j ){ 20 res=max(res,dp[i][j]); 21 } 22 } 23 cout< "\n"; 24 return 0; 25 }
D:Cow and Fields
题意:有k个特殊点,必须在其中两个之间加一条路径,问选哪两个可以是从1到n的最短距离最长。
题解:设选的两个点为a、b。先搜每个点距离1和n的距离。设dis(1,a)+dis(b,n) 1 //D
2 #include
E:Cow and Treats
F:Cow and Vacation
G:Cow and Exercise