AtCoder Beginner Contest 104
A - Rated for Me
给定每个分数段所代表的比赛,问当前分数段是哪个比赛
直接模拟(less than是<,不是≤)
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 int main() { 5 int n; scanf("%d", &n); 6 if(n < 1200) puts("ABC"); 7 else if(n < 2800) puts("ARC"); 8 else puts("AGC"); 9 }
B - AcCepted
字符串S给出。 S的每个字母都是大写字母或小写字母。 确定S是否满足以下所有条件。
S的第一个字母是大写字母A.
只有一个大写的C包含在S开头的第三个字符和结尾的第二个字符(包括两端)之间。
除A和C外,S的所有字母均为小写字母。
也是直接模拟(需要保证读对题了)
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 char s[20]; 5 int n; 6 int main() { 7 scanf("%s", s + 1); 8 int flag = 1; 9 10 int n = strlen(s + 1), cnt = 0; 11 flag = s[1] == 'A'; 12 // [3, n - 2] 13 cnt = 0; 14 for(int i = 3 ; i <= n - 1 ; ++ i) if(s[i] == 'C') ++ cnt; 15 if(cnt != 1) flag = 0; 16 17 cnt = 0; 18 for(int i = 1 ; i <= n ; ++ i) 19 if(!('a' <= s[i] && s[i] <= 'z')) { 20 if(s[i] != 'A' && s[i] != 'C') 21 flag = 0; 22 } 23 24 25 if(flag) puts("AC"); 26 else puts("WA"); 27 }
C - All Green
有D(≤10)种问题,第i种问题的个数有p[i]个,每做完一个第i种问题会获得100i的得分
当做完第i种问题后,可以获得额外的c[i]的得分(当然可以不完成所有的题)
问如果想要得分不低于G,至少需要做多少题
暴力枚举一下哪些问题是一定做完的,然后从n往1扫一遍,贪心的做题来获得最大得分
1 #include <bits/stdc++.h> 2 using namespace std; 3 4 int D, G, p[20], c[20], vis[20]; 5 6 struct T { 7 int p, c; 8 }; 9 10 int sol() { 11 int res = 0, rem = G; 12 for(int i = 1 ; i <= D ; ++ i) { 13 if(vis[i]) { 14 res += p[i]; 15 rem -= 100 * i * p[i] + c[i]; 16 } 17 } 18 for(int i = D ; i >= 1 ; -- i) { 19 if(vis[i] == 0) { 20 if(rem > 0) { 21 if(rem - 100 * i * p[i] >= 0) { 22 // return 1000000000; 23 rem -= 100 * i * p[i] + c[i]; 24 res += p[i]; 25 } else { 26 // rem - 100 * i * x >= 0 27 // x <= rem / (100 * i) 28 int x = rem / (100 * i); 29 rem -= 100 * i * x; 30 res += x; 31 } 32 } 33 } 34 } 35 return rem <= 0 ? res : 1000000000; 36 } 37 38 int main() { 39 scanf("%d%d", &D, &G); 40 for(int i = 1 ; i <= D ; ++ i) { 41 scanf("%d%d", &p[i], &c[i]); 42 } 43 int ans = 1000000000; 44 for(int s = 0 ; s < (1 << D) ; ++ s) { 45 for(int i = 1 ; i <= D ; ++ i) vis[i] = ((s >> (i - 1)) & 1); 46 ans = min(ans, sol()); 47 // cout << s << ' ' << sol() << endl; 48 } 49 printf("%d\n", ans); 50 }
D - We Love ABC
给定字符串T,T是由"ABC?"这4种字符中的一种构成
"?"可以替换成"ABC"中的一种
设有Q个"?",那么就一共有3Q种可能的字符串
对于每一个字符串,求出它的(A,B,C)的点对个数(有序),将这些个数都加起来输出
对于点对(A,B,C)来说,只要在B处统计之前有多少个A和之后有多少个C就行
以A的个数为例,设当前枚举的B之前有x个"?",如果原先的位置就是A,那么在3x种字符串中都会有这个贡献,如果原先的位置是"?",那么在3x-1种字符串中会产生这个贡献
1 #include <bits/stdc++.h> 2 using namespace std; 3 const int N = 1e5 + 10, p = 1e9 + 7; 4 char s[N]; 5 6 int pw(int a, int b) { 7 int r = 1; 8 for( ; b ; b >>= 1, a = (long long) a * a % p) if(b & 1) r = (long long) r * a % p; 9 return r; 10 } 11 12 int pre[N][4]; // 0:A 1:B 2:C 3:? 13 int sub[N][4]; 14 15 int main() { 16 scanf("%s", s + 1); 17 int n = strlen(s + 1); 18 for(int i = 1 ; i <= n ; ++ i) { 19 memcpy(pre[i], pre[i - 1], sizeof pre[i]); 20 pre[i][s[i] == '?' ? 3 : s[i] - 'A'] ++; 21 } 22 for(int i = n ; i ; -- i) { 23 memcpy(sub[i], sub[i + 1], sizeof sub[i]); 24 sub[i][s[i] == '?' ? 3 : s[i] - 'A'] ++; 25 } 26 long long ans = 0; 27 for(int i = 1 ; i <= n ; ++ i) { 28 // cout << pre[i][0] << ' ' << pre[i][1] << ' ' << pre[i][2] << ' ' << pre[i][3] << endl; 29 if(s[i] == 'B' || s[i] == '?') { 30 31 // cout << "count in: " << i << endl; 32 33 long long x = 0; 34 long long y = 0; 35 x = (long long) pre[i - 1][0] * pw(3, pre[i - 1][3]) % p; 36 if(pre[i - 1][3]) y = (long long) pre[i - 1][3] * pw(3, pre[i - 1][3] - 1) % p; 37 38 long long z = x + y; 39 40 x = y = 0; 41 x = (long long) sub[i + 1][2] * pw(3, sub[i + 1][3]) % p; 42 if(sub[i + 1][3]) y = (long long) sub[i + 1][3] * pw(3, sub[i + 1][3] - 1) % p; 43 44 ans = (ans + z * (x + y) % p) % p; 45 46 } 47 } 48 printf("%lld\n", ans); 49 }