写在前面:
因为最近cf打得非常惨烈,也发现了自己在暴力模拟题的思维能力和代码实现能力严重欠缺(尤其是代码实现能力,这也造成了我在组队赛中心理上非常抗拒上机写题)
受到大佬这篇文章的启发,决定开始刷atcoder的ABC中的 problem B、C,希望在大二开学前cf能顺利打上1400+
之后会对每天刷的atcoder进行记录以监督自己坚持练习
ABC310
B - Strictly Superior
题意
给出每个商品的价格和包含的功能,问是否有一个商品严格优于另一个商品
i 严格优于 j 必须满足下列条件之一:
- i 比 j 便宜,i 的功能包含了 j 的所有功能
- i 和 j 价格一样,i 的功能包含 j 的所有功能且比 j 的功能多
思路
暴力,判断当前的两个物品是否满足上述条件
代码
原始代码
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int n, m;
cin >> n >> m;
vector<int> price(n);
vector<int> func_num(n);
int func[110][110];
for (int i = 0; i < n; i ++ )
{
cin >> price[i] >> func_num[i];
for (int j = 0; j < func_num[i]; j ++ ) cin >> func[i][j];
}
for (int i = 0; i < n; i ++ )
{
for (int j = 0; j < n; j ++ )
{
if (i == j) continue;
// 判断i是否严格优于j
if (price[i] > price[j]) continue;
else if (price[i] == price[j])
{
if (func_num[i] <= func_num[j]) continue;
else
{
int l = 0, r = 0;
while (l < func_num[i] && r < func_num[j])
{
if (func[i][l] > func[j][r]) break;
else if (func[i][l] == func[j][r]) l ++, r ++ ;
else l ++ ;
}
if (r == func_num[j])
{
cout << "Yes" << endl;
return 0;
}
}
}
else
{
if (func_num[i] < func_num[j]) continue;
else
{
int l = 0, r = 0;
while (l < func_num[i] && r < func_num[j])
{
if (func[i][l] > func[j][r]) break;
else if (func[i][l] == func[j][r]) l ++, r ++ ;
else l ++ ;
}
if (r == func_num[j])
{
cout << "Yes" << endl;
return 0;
}
}
}
}
}
cout << "No" << endl;
}
优化代码
这里参考了jls的代码,发现自己还是思考少了导致代码就很长…
#include <bits/stdc++.h>
using namespace std;
const int N = 110;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int n, m;
cin >> n >> m;
vector<int> price(n);
vector<bitset<N>> func(n);
for (int i = 0; i < n; i ++ )
{
int x;
cin >> price[i] >> x;
for (int j = 0; j < x; j ++ )
{
int k;
cin >> k;
func[i][k - 1] = 1;
}
}
for (int i = 0; i < n; i ++ )
{
for (int j = 0; j < n; j ++ )
{
if (price[i] <= price[j] && (func[i] & func[j]) == func[j] && (price[i] < price[j] || func[i] != func[j]))
{
cout << "Yes" << endl;
return 0;
}
}
}
cout << "No" << endl;
}
C - Reversible
题意
正着看反着看一样的字符串算作同一种字符串,给出若干个字符串,问有多少种
思路
我的代码里用了map来存储,实际上好像也没有必要,只需要一个有查找函数的容器就可以了,先把所有字符串存进去,再从头遍历每一个字符串,记录下已经遍历过的,统计种类数即可(正反算同一种)
代码
#include <bits/stdc++.h>
using namespace std;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int n;
map<string, int> m;
cin >> n;
vector<string> ss(n);
for (int i = 0; i < n; i ++ )
{
string s;
cin >> s;
ss[i] = s;
if (m.find(ss[i]) == m.end()) m[ss[i]] = 1;
else m[ss[i]] ++ ;
}
int ans = 0;
for (int i = 0; i < n; i ++ )
{
if (m[ss[i]] != 0)
{
string s = ss[i];
m[s] = 0; // 表示该种情况已经计算过
reverse(s.begin(), s.end());
m[s] = 0;
ans ++ ;
}
}
cout << ans;
}
ABC309
B - Rotate
题意
给出一个二维数组,把最外面一圈顺时针转一下再输出
思路
记录下四个顶点的,然后直接挪
代码
#include <bits/stdc++.h>
using namespace std;
const int N = 110;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int n;
cin >> n;
char g[N][N];
for (int i = 0; i < n; i ++ )
for (int j = 0; j < n; j ++ )
cin >> g[i][j];
char a = g[0][0], b = g[0][n - 1], c = g[n - 1][0], d = g[n - 1][n - 1];
for (int i = n - 1; i > 0; i -- )
{
g[0][i] = g[0][i - 1];
g[i][n - 1] = g[i - 1][n - 1];
}
for (int i = 0; i < n - 1; i ++ )
{
g[n - 1][i] = g[n - 1][i + 1];
g[i][0] = g[i + 1][0];
}
g[0][1] = a, g[1][n - 1] = b, g[n - 2][0] = c, g[n - 1][n - 2] = d;
for (int i = 0; i < n; i ++ )
{
for (int j = 0; j < n; j ++ )
cout << g[i][j];
cout << endl;
}
}
C - Medicine
题意
从第一天开始,告诉你吃多少药,每种药每天吃多少片、吃多少天,问多少天之后吃的药片个数小于等于给定值 k
思路
按天数从大到小排列,用 sum 累加当前吃的药的片数,直到大于 k,输出这一天的后一天
代码
#include <bits/stdc++.h>
using namespace std;
using i64 = long long;
typedef pair<int, int> PII;
bool cmp(PII a, PII b)
{
return a.first > b.first;
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(0); cout.tie(0);
int n, k;
cin >> n >> k;
i64 sum = 0;
vector<pair<int, int>> messages(n);
for (int i = 0; i < n; i ++ )
{
int a, b;
cin >> a >> b;
messages[i] = make_pair(a, b);
}
sort(messages.begin(), messages.end(), cmp);
if (k < messages[0].second)
{
cout << messages[0].first + 1;
return 0;
}
for (int i = 0; i < n; i ++ )
{
sum += messages[i].second;
if (sum > k)
{
cout << messages[i].first + 1;
return 0;
}
}
cout << 1;
return 0;
}