Codeforces Round #643 (Div. 2)(A, B, C, D, E)
Codeforces Round #643 (Div. 2)
Sequence with Digits
思路
一道暴力題,猜想在某一步一定會出現0,于是懷著忐忑提交了代碼,結果還真的是這樣。
代碼
#include <bits/stdc++.h>using namespace std;typedef long long ll;ll judge(ll x) {int minn = x % 10, maxn = x % 10;ll temp = x;temp /= 10;while(temp) {minn = min(int(temp % 10), minn);maxn = max(int(temp % 10), maxn);temp /= 10;}return x + minn * maxn; }int main() {// freopen("in.txt", "r", stdin);int t;scanf("%d", &t);while(t--) {ll ans, n;scanf("%lld %lld", &ans, &n);for(ll i = 0; i < n - 1; i++) {ll temp = judge(ans);if(temp == ans) break;ans = temp;}printf("%lld\n", ans);}return 0; }Young Explorers
思路
應該是一個貪心吧。
題意是對于一個分數為eee的選手,只能加入人數大于等于eee的組里,所以我們取每一組的最大值剛好等于其人數,這樣就最大化的利用了所有的人,當然進行這一步之前必須得先排序。
代碼
#include <bits/stdc++.h>using namespace std;#define IOS ios::sync_with_stdio(false); cin.tie(0); cout.tie(0) typedef long long ll;const int N = 2e5 + 10;int a[N];int main() {// freopen("in.txt", "r", stdin);IOS;int t;cin >> t;// scanf("%d", &t);while(t--) {int n;cin >> n;for(int i = 0; i < n; i++)cin >> a[i];int sum = 0, ans = 0;sort(a, a + n);for(int i = 0; i < n; i++) {sum++;if(a[i] <= sum) {sum = 0;ans++;}}cout << ans << "\n";}return 0; }Count Triangles
思路
這題是看了別人的思路才寫出來的,我一開始一直在枚舉zzz邊試圖去找另外兩條邊的范圍,但是一直wa。
- 我們考慮枚舉x+yx + yx+y的范圍, min(c+1,a+b)<=i<=b+cmin(c + 1, a + b) <= i <= b + cmin(c+1,a+b)<=i<=b+c。
- 通過x的最大值我們可以確定y的最小值,同時我們也可以通過x的最小值確定y的最大值。
當x=ax = ax=a,最大的ymax=min(i?a,c)y_{max} = min(i - a, c)ymax?=min(i?a,c),當y=by = by=b,最大的xmax=min(i?b,b)x_{max} = min(i - b, b)xmax?=min(i?b,b)
通過這個我們可以鎖定任意的真正的最小的x∣∣yx || yx∣∣y,我們xmin=i?ymaxx_{min} = i - y_{max}xmin?=i?ymax?,ymin=i?xmaxy_{min} = i - x_{max}ymin?=i?xmax?
這里我們可以得到任意的一段符合條件的x,y的組合,num=(xmax?xmin+1)=(ymax?ymin+1)num = (x_{max} - x_{min} + 1) = (y_{max} - y_{min} + 1)num=(xmax??xmin?+1)=(ymax??ymin?+1)
然后zzz的取值區間長度是long=min(d?c+1,i?c)long = min(d - c + 1, i - c)long=min(d?c+1,i?c)。
我們每次枚舉的區間答案就是ans+=num?longans += num * longans+=num?long
代碼
#include <bits/stdc++.h>using namespace std;#define IOS ios::sync_with_stdio(false); cin.tie(0); cout.tie(0) typedef long long ll;int main() {// freopen("in.txt", "r", stdin);IOS;ll a, b, c, d, ans = 0;cin >> a >> b >> c >> d;for(int i = max(a + b, c + 1); i <= b + c; i++) {int x = min(i - b, b), y = min(i - a, c);x = i - x;ll l = min(i - c, d - c + 1);ans += l * (y - x + 1);}cout << ans << "\n";return 0; }Game With Array
思路
一道構造題,這題應該是比較好想的,當2?n>s2 * n > s2?n>s的時候,我們至少會出現兩個一,然后剩下的全是2,這里我們顯然可以得到我們所需要的和為sss的所有二進制數,所以這個是侯一定是不可能有解的。
當2?n<=s2 * n <= s2?n<=s的時候我們如何構造,只需要取n?1n - 1n?1個一,然后最后一個數是s?n+1s - n + 1s?n+1就行了,最后的kkk取nnn這樣就可以保證答案的有解性。
代碼
#include <bits/stdc++.h>using namespace std;#define IOS ios::sync_with_stdio(false); cin.tie(0); cout.tie(0) typedef long long ll;int main() {// freopen("in.txt", "r", stdin);IOS;int n, s;cin >> n >> s;if(2 * n > s) cout << "NO\n";else {cout << "YES\n";for(int i = 0; i < n - 1; i++)cout << "1 ";cout << s - (n - 1) << "\n";cout << n << "\n";}// int t;// cin >> t;// // scanf("%d", &t);// while(t--) {// }return 0; }Restorer Distance
思路
因為push和move這兩個操作,我們比較容易發現這兩個操作好像在最大值最小值兩頭是等價的,因此當在最大最小值中間可能存在一個最優值,使操作成本最低。
通過上面的分析我們可以大致的得到這是一個凹函數,并且存在最極小值,因此我們可以考慮三分去的到這個最小值。
代碼
#include <bits/stdc++.h>using namespace std;typedef long long ll;const int N = 1e5 + 10;int a[N], n, A, R, M;ll f(int x) {ll sum1 = 0, sum2 = 0;//分別記錄大于當前值的數量,和小于當前值的數量。for(int i = 1; i <= n; i++) {if(a[i] > x) sum1 += a[i] - x;else if(a[i] < x) sum2 += x - a[i];}ll ans = 0;ll mid = min(sum2, sum1);ans += mid * M;sum1 -= mid, sum2 -= mid;//優先考慮從一個移到另一個上。if(sum1) ans += sum1 * R;if(sum2) ans += sum2 * A;return ans; }int main() {// freopen("in.txt", "r", stdin);scanf("%d %d %d %d", &n, &A, &R, &M);M = min(M, A + R);//這個操作可以等同是前兩個操作的和,取一個最小值。for(int i = 1; i <= n; i++)scanf("%d", &a[i]);int l = 0, r = 1e9;while(l < r) {int lmid = l + (r - l) / 3;int rmid = r - (r - l) / 3;if(f(lmid) >= f(rmid)) l = lmid + 1;else r = rmid - 1;}printf("%lld\n", min(f(l), f(r)));return 0; }總結
以上是生活随笔為你收集整理的Codeforces Round #643 (Div. 2)(A, B, C, D, E)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 罗红霉素分散片是消炎药吗
- 下一篇: 什么是肺大泡