UVa 12545 Bits Equalizer (贪心)
Posted dwtfukgv
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了UVa 12545 Bits Equalizer (贪心)相关的知识,希望对你有一定的参考价值。
题意:给出两个等长的字符串,0可以变成1,?可以变成0和1,可以任意交换s中任意两个字符的位置,问从s变成t至少需要多少次操作。
析:先说我的思路,我看到这应该是贪心,首先,如果先判断s能不能变成t,就计算t中的1和s中的1。
然后算出t比s多多少1,然后先考虑把?变成1是最优的,如果不够就只能把0变成1,切不可把?变成1,因为这样要两步,
不是最优,而把0变成1是一步。然后把剩下的?变成1(如果1还不够)或者是0(1够了)。最后是计算要交换的次数,
这个只要统计不同的位置有多少即可,别忘了1可能还不够,这个也要算上,怎么算呢,想一下,先把0变成1,再交换,
所以说是要先加上要变化的1,然后在不同位置中也加上,然后除以2.相加就是结果。
然而我觉得自己写的太烂了,上网百度,看到大神们写的就是简洁明了。。。。
是这么想的,首先交换是最优的,因为一次操作能满足两个,然后再去找1-0和?-1的进行交换,为什么呢?因为我们看s中的1是不是多了,
如果少,没关系,可以直接把?变成1,如果多了就无解了,所以要比较这个。最后再加上?-0即可,这个只要一步。
大神就是牛逼。
代码如下:
这是我的代码
#include <cstdio> #include <cstring> #include <iostream> using namespace std; const int maxn = 100 + 10; char s[maxn], t[maxn]; int main(){ // freopen("in.txt", "r", stdin); int T; cin >> T; for(int kase = 1; kase <= T; ++kase){ scanf("%s %s", s, t); int n = strlen(s); int cnts1 = 0, cntt0 = 0, cnts0 = 0;//cnts1是s串中1的个数,同理其他的 for(int i = 0; i < n; ++i){ if(‘0‘ == t[i]) ++cntt0; if(‘0‘ == s[i]) ++cnts0; else if(‘1‘ == s[i]) ++cnts1; } int cntt1 = n - cntt0;//1的个数 int cntss = n - cnts0 - cnts1;//?的个数 int det = cntt1 - cnts1;//s和t差多少1 printf("Case %d: ", kase); if(det < 0){ printf("-1\n"); continue; }//1太多了,把问号全改了都不够 int cnt = 0; for(int i = 0; i < n; ++i) if(det && ‘?‘ == s[i] && t[i] == ‘1‘){ ++cnt; s[i] = ‘1‘; --det;//把?变成1 } for(int i = 0; i < n; ++i)//把0变成1 if(det && ‘0‘ == s[i] && ‘1‘ == t[i]){ --det; s[i] = ‘1‘; ++cnt; } for(int i = 0; i < n; ++i){//把剩下的?变成0或1 if(det && ‘?‘ == s[i]){ ++cnt; s[i] = ‘1‘; --det; } if(!det && ‘?‘ == s[i]){ ++cnt; s[i] = ‘0‘; } } int x = 0; for(int i = 0; i < n; ++i)//计算不同的数, if(s[i] != t[i]) ++x; cnt += det;//计算要要交换的次数 cnt += (x + det)/ 2; printf("%d\n", cnt); } return 0; }
下面是我参考大神们的代码写的:
#include <cstdio> #include <cstring> #include <iostream> using namespace std; const int maxn = 100 + 10; char s[maxn], t[maxn]; int main(){ int T; cin >> T; for(int kase = 1; kase <= T; ++kase){ scanf("%s %s", s, t); int n = strlen(s); int zero_one = 0, one_zero = 0, q_one = 0, q_zero = 0; for(int i = 0; i < n; ++i){ if(s[i] == ‘0‘ && t[i] == ‘1‘) ++zero_one; else if(s[i] == ‘1‘ && t[i] == ‘0‘) ++one_zero; else if(s[i] == ‘?‘ && t[i] == ‘0‘) ++q_zero; else if(s[i] == ‘?‘ && t[i] == ‘1‘) ++q_one; } int cnt = 0; while(zero_one && one_zero){ --zero_one; --one_zero; ++cnt; } while(q_one && one_zero){ --q_one; --one_zero; cnt += 2; } if(one_zero) cnt = -1; else cnt += q_zero + zero_one + q_one; printf("Case %d: %d\n", kase, cnt); } return 0; }
以上是关于UVa 12545 Bits Equalizer (贪心)的主要内容,如果未能解决你的问题,请参考以下文章