Codeforces Round #521 (Div. 3) CDE

C

问删掉在数组中一个数后,剩下的数组中,是否存在一个数时其它所有数的和。

遍历每一个数,假设删掉它后,剩下的数中取一个最大值,看他的值是不是数组之和的一半,是的话就成立。

 1 #include <bits/stdc++.h>
 2 #define ll long long
 3 using namespace std;
 4 const int N = 2e5+10;
 5 ll a[N], n;
 6 vector<ll> v;
 7 int main() {
 8     cin >> n;
 9     ll sum = 0;
10     priority_queue<ll> que;
11     for(int i = 1; i <= n; i ++) cin >> a[i], sum += a[i], que.push(a[i]);
12     int ans = 0;
13     // cout << sum << ' ' << que.top() << endl;
14     for(int i = 1; i <= n; i ++) {
15         if(que.top() == a[i]) {
16             que.pop();
17             sum -= a[i];
18             if(sum == que.top()*2) ans++, v.push_back(i);
19             sum += a[i];
20             que.push(a[i]);
21         } else {
22             sum -= a[i];
23             if(sum == que.top()*2) ans++, v.push_back(i);
24             sum += a[i];
25         }
26     }
27     printf("%d\n",ans);
28     for(auto x : v) printf("%lld ", x);printf("\n");
29     return 0;
30 }

有一个数组,可以选定一个子集,看最大能删除多少次,输出那个子集。

二分,检查当前最大删除次数时m时,是否成立。

 1 #include <bits/stdc++.h>
 2 #define ll long long
 3 using namespace std;
 4 const int N = 2e5+10;
 5 int a[N], n, k, x;
 6 bool cmp(int x, int y) { return x > y;}
 7 bool ok(int m) {
 8     int ans = 0;
 9     for(int i = 0; i < N; i ++) if(a[i])ans += a[i]/m;
10     return ans >= k;
11 }
12 int main() {
13     cin >> n >> k;
14     for(int i = 1; i <= n; i ++) {
15         cin >> x;
16         a[x]++;
17     }
18     int l = 1, r = n/k, MAX = 0;
19     while (l <= r) {
20         int m = (l+r) >> 1;
21         if(ok(m)) {
22             MAX = max(MAX, m);
23             l = m + 1;
24         } else r = m-1;
25     }
26     int ans = 0;
27     for(int i = 0; i < N; i ++) {
28         for(int j = 0; j < a[i]/MAX; j ++) {
29             if(ans == k) break;
30             printf("%d%c",i," \n"[ans==k-1]);
31             ans ++;
32         }
33     }
34     return 0;
35 }

E

有很多主题,每个主题都有一些题目,选定一些主题,后面主题的问题数一定时前面的两倍,第一个主题的问题数随意,求最大的问题数。

水过了,如果存在1,2,3...100000的主题都是1个问题,100001的问题数是100000时就肯定过不了。

 1 #include <bits/stdc++.h>
 2 #define ll long long
 3 using namespace std;
 4 const int N = 2e5+10;
 5 int x, n, a[N], cnt;
 6 map<int,int> mp;
 7 bool vis[N];
 8 std::vector<int> v;
 9 int main() {
10     cin >> n;
11     for(int i = 1; i <= n; i ++) cin >> x, mp[x]++;
12     priority_queue<int, vector<int>, greater<int> > que;
13     for(auto m : mp) a[cnt++] = m.second, que.push(m.second);
14     sort(a,a+cnt);
15     int MAX = 0;
16     for(int i = 1; i <= a[cnt-1]; i ++) {
17         int x = i, ans = 0;
18         while(que.size()) {
19             while(que.size() && que.top() < x) que.pop();
20             if(que.empty()) break;
21             ans += x;
22             que.pop();
23             x *= 2;
24         }
25         for(int i = 0; i < cnt; i ++) que.push(a[i]);
26         MAX = max(MAX, ans);
27     }
28     printf("%d\n",MAX);
29     return 0;
30 }

猜你喜欢

转载自www.cnblogs.com/xingkongyihao/p/9973420.html