洛谷 P5595 【XR-4】歌唱比赛
洛谷 P5595 【XR-4】歌唱比赛
思路&&代码
这是一道普及-的题目
有一道题和这么一道题很类似,可以先去做这道题,再来做这个,链接:
然后我们来考虑这道题的做法
既然是\(special\ judge\),我们就可以直接乱搞了,只用\(0\)和\(1\)两个数,我们就可以\(A\)掉它啦~~
拿到题目的第一眼其实是有一点点懵逼的,然后读一读就会发现并不难,我们很容易就可以想到一个思路:从前往后扫,如果此时的字符为\(X\),那就让\(X\)这个数的这一位比\(Y\)大,如果此时的字符为\(Y\),那就让\(Y\)这个数的这一位比\(X\)大,如果此时的字符为\(Z\),那么就让\(X\)和\(Y\)两个数的这一位相等
思路简直不要太完美
然后我兴高彩烈的交了一发,\(74\)分
为什么??因为没有判断无解的情况,我忘记了还有样例\(4\)这种无解的情况,这是我最菜的地方……
那么我们来看一下,什么样的情况才算无解
其实这个也比较明显,就像下面这种情况\(XXXZZYYZ\),如果前面出现了一个\(Z\),而后面不是\(Z\),但之后又出现了\(Z\),就是无解,为什么呢?因为按照题意来说,\(Z\)表示的是:从\(Z\)这一位开始后面所有的数字都是相等的,即到目前为止\(X\)和\(Y\)两数相等。如果前面有了\(Z\),而中间又有了\(X\)或\(Y\),很明显是不对的,所以我们就可以先\(O(n)\)判断一下会不会出现无解的情况,代码如下
for(int i = 1; i <= len; i++) {
if(s[i] == 'Z') now = 1;//now表示有没有Z
if(s[i] != 'Z' && now) return cout << "-1\n", 0;
//如果从前往后扫,已经出现了Z,后面就不能再出现X或Y,如果出现,即是无解
}
然后就做完了,完整的代码如下
/*
By:Loceaner
*/
#include <cstdio>
#include <cstring>
#include <iostream>
using namespace std;
inline int read() {
char c = getchar();
int x = 0, f = 1;
for( ; !isdigit(c); c = getchar()) if(c == '-') f = -1;
for( ; isdigit(c); c = getchar()) x = (x << 3) + (x << 1) + (c ^ 48);
return x * f;
}
const int N = 1e6 + 11;
char s[N], a[N], b[N];
int now;
int main() {
scanf("%s", s + 1);
int len = strlen(s + 1);
for(int i = 1; i <= len; i++) {
if(s[i] == 'Z') now = 1;
if(s[i] != 'Z' && now) return cout << "-1\n", 0;
}
for(int i = 1; i <= len; i++) {
if(s[i] == 'X') a[i] = '1', b[i] = '0';
else if(s[i] == 'Y') a[i] = '0', b[i] = '1';
else if(s[i] == 'Z') a[i] = '1', b[i] = '1';
}
printf("%s\n%s", a + 1, b + 1);
return 0;
}
转载不必联系作者,但请声明出处