Educational Codeforces Round 76 (Rated for Div. 2)

A - Two Rival Students

题意:共n个人排一排,两个人,位于a,b,相邻位置交换至多x次,求max abs(a-b)。

题解:贪心,能往左就往左,能往右就往右,超过x次就只算x次就行了。

 1 #include <iostream>  
 2 #include<algorithm>
 3 #include<cstdio>
 4 #include<cmath>
 5 using namespace std;  
 6 int t,n,x,a,b;
 7 int main()
 8 {
 9     cin>>t;
10     while(t)
11     {
12         t--;
13         cin>>n>>x>>a>>b;
14         if(a>b) swap(a,b);
15         int l1=a-1;int l2=n-b;
16         int tem=min(l1+l2,x);
17         printf("%d\n",abs(a-b)+tem);
18     }
19     return 0;
20 }

B - Magic Stick

题意:给定x,两种操作。

  若x>1,x--。

  若x为偶数,x=x*3/2.

问能否得到给定的y。

题解:x可以无限减下来,所以考虑开始的几个数就好。x=1无法变化,x=2或3时最大能变成3,x=4->6->9->8->12...  只要x>3就能无限上去。

 1 #include <iostream>  
 2 #include<algorithm>
 3 #include<cstdio>
 4 #include<cmath>
 5 using namespace std;  
 6 unsigned long long t,x,y;
 7 int main()
 8 {
 9     cin>>t;
10     while(t)
11     {
12         t--;bool f=0;
13         cin>>x>>y;
14         if(x==1&&y==1)f=1;
15         if(x==3||x==2)
16         if(y<=3)f=1;
17         if(x>3)f=1;
18         cout<<(f?"YES":"NO")<<endl;
19     }
20     return 0;
21 }

 

C. Dominated Subarray

题意:给定数组an,[l,r]区间被dominate当且仅当区间众数唯一,求最小被dominate的区间长度。

题解:贪心。

  某区间只需考虑众数出现次数为2,若众数出现次数大于2,则出现次数为2的区间显然更短。

  那就只用记录前一个同样的数出现的位置就行了。

 1 #include <iostream>  
 2 #include<algorithm>
 3 #include<cstdio>
 4 #include<cmath>
 5 #include<cstring>
 6 using namespace std;  
 7 long long t,n;
 8 int a[1000000];
 9 int vis[1000000];
10 int main()
11 {
12     ios::sync_with_stdio(0);
13     cin>>t;
14     while(t)
15     {
16         memset(vis,0,sizeof(vis));
17         t--;
18         cin>>n;int ans=n+1;
19         for(int i=1;i<=n;i++)
20         {
21             cin>>a[i];
22             if(vis[a[i]]==0)
23             vis[a[i]]=i;
24             else
25             {
26                 ans=min(ans,i-vis[a[i]]+1);
27                 vis[a[i]]=i;
28             }
29         }
30         if(n==1)
31         cout<<"-1"<<endl;
32         else
33         {
34             if(ans==n+1)cout<<"-1"<<endl;
35             else
36             cout<<ans<<endl;
37         }
38     }
39     return 0;
40 }

D - Yet Another Monster Killing Problem

题意:n个怪物,攻击力ai,从左往右打。m个英雄,pi攻击力,遇到打不过的就回城,si耐久,即一天最多打si个怪,然后回城,英雄不限使用次数,求最少几天打完怪,打不过输出-1.

题解:贪心,对英雄排序,攻击力为第一关键字,耐久第二关键字。然后二分查找某一天最多能打到哪里。

  贴个外国友人的代码,觉得实现的挺漂亮。ps:不是我的啊。

  pps:其实拿结构排序方便点,但是下面写很漂亮。

 1 #include <bits/stdc++.h>
 2 #define DB(x) cerr << __LINE__ << ": " << #x << " = " << (x) << endl
 3 using namespace std;
 4  
 5 int main() {
 6     int t;
 7     cin >> t;
 8     while(t--) {
 9         int n, mx1 = -1, mx2 = -1;
10         cin >> n;
11         vector<int> monster(n);
12         for(int i = 0; i < n; ++i) {
13             cin >> monster[i];
14             mx1 = max(mx1, monster[i]);
15         }
16         int m;
17         cin >> m;
18         vector<pair<int, int> > h(m), hero;
19         for(int i = 0; i < m; ++i) {
20             cin >> h[i].first >> h[i].second;
21             mx2 = max(mx2, h[i].first);
22         }
23         if(mx2 < mx1) {
24             cout << "-1\n";
25             continue;
26         }
27         sort(h.begin(), h.end());
28         hero.push_back(h[m-1]);
29         int cnt1 = 0;
30         for(int i = m-2; i > -1; --i) {
31             if(h[i].second > hero[cnt1].second) {
32                 ++cnt1;
33                 hero.push_back(h[i]);
34             }
35         }
36         reverse(hero.begin(), hero.end());
37         // for(int i = 0; i < hero.size(); ++i) DB(hero[i].first);
38         int start = 0, ans = 0;
39         while(start < n) {
40             ++ans;
41             int cnt = 0, mx = -1;
42             for(; start < n; ++start) {
43                 ++cnt;
44                 mx = max(mx, monster[start]);
45                 int lo = 0, hi = hero.size() - 1, pos = 0;
46                 while(lo <= hi) {
47                     int mid = (lo + hi) / 2;
48                     if(hero[mid].first >= mx && hero[mid].second >= cnt) {
49                         // DB(ans);
50                         // DB(start);
51                         // DB(mid);
52                         pos = 1;
53                         break;
54                     }
55                     else if(hero[mid].first >= mx) {
56                         hi = mid - 1;
57                     }
58                     else if(hero[mid].second >= cnt) {
59                         lo = mid + 1;
60                     }
61                     else {
62                         break;
63                     }
64                 }
65                 if(!pos) {
66                     // DB(start);
67                     break;
68                 }
69             }
70         }
71         cout << ans << "\n";
72     }
73     return 0;
74 }

待续。。。

posted @ 2019-11-14 16:03  慎独191812  阅读(178)  评论(0编辑  收藏  举报

Contact with me