D. Ingenuity-2
https://codeforces.com/problemset/problem/1974/D
题意:两个物体R和H位于二维坐标系原点,现给定一组指定的操作,每个操作可以任意分给R或者H,操作包含上下左右移动,并且要求每个物体至少移动一次,问最终两个物体能否在同一个终点?输出每个操作分给了哪个物体。
思路:上和下的移动可以抵消,左和右的移动可以抵消,先将这些操作统计出来,分给两个人。然后考虑剩下的操作是否可以完全分成两份一模一样的,如果不可以,那说明不可行。如果可以,则将剩下的操作轮着分给两个人即可。
总结:题目要求每个物体至少操作一次,那么就必须在一开始做抵消操作分配的时候,就保证尽可能的让每个物体都分配到操作。
inline void solve() {
int n;
cin >> n;
string s;
cin >> s;
string ans(n, '!');
map<char, int> mapp;
for (auto c : s) {
mapp[c] ++;
}
if (mapp['N'] > 0 && mapp['S'] > 0) {
int cnt = min(mapp['N'], mapp['S']);
mapp['N'] -= cnt;
mapp['S'] -= cnt;
for (int i = 0, j = 0, k = 0; min(i, j) < cnt; ++k) {
if (s[k] == 'N' && i < cnt) {
ans[k] = !i ? 'R' : 'H';
i ++;
}
else if (s[k] == 'S' && j < cnt) {
ans[k] = !j ? 'R' : 'H';
j ++;
}
}
}
if (mapp['E'] > 0 && mapp['W'] > 0) {
int cnt = min(mapp['E'], mapp['W']);
mapp['E'] -= cnt;
mapp['W'] -= cnt;
for (int i = 0, j = 0, k = 0; min(i, j) < cnt; ++k) {
if (s[k] == 'E' && i < cnt) {
ans[k] = !i ? 'H' : 'R';
i ++;
}
else if (s[k] == 'W' && j < cnt) {
ans[k] = !j ? 'H' : 'R';
j ++;
}
}
}
for (auto [x, y] : mapp) {
if (y & 1) {
cout << "NO\n";
return;
}
}
for (int i = 0; i < n; ++i) {
if (ans[i] != '!') {
continue;
}
if (mapp[s[i]] & 1) {
ans[i] = 'R';
}
else {
ans[i] = 'H';
}
mapp[s[i]] --;
}
int cnt = count(ans.begin(), ans.end(), 'R');
if ((cnt == n || cnt == 0)) {
cout << "NO\n";
return;
}
cout << ans << '\n';
}

浙公网安备 33010602011771号