题意
给你一个有n个字符组成的01串,让你构造一个a,b,a,b都是由’(’’)'组成,构造合法的a,b,且如果s[i]=‘1’的时候,a[i]==b[i],如果s[i]=‘0’的时候保证a[i]!=b[i]。
思路
我们通过这个题可以发现一些性质。
1.
1.
1. 0的数量和1的数量必须都是偶数。
2.
2.
2. 第一个数和最后一个数必须都是1。
通过这两个性质,我们可以知道,a和b的第一位和最后一位肯定刚好是’(‘和’)’,0的数量和1的数量都是偶数,我们可以0和0匹配,1和1匹配,有些人可能会有疑问,这样为什么是可行的。
我来
简单证明一下。
如果1的匹配的话肯定不用说,一定可以构造成功,因为有偶数个1,a和b中在1的位置上是完全相同的。
0的匹配的时候,如果我们按照0和0来匹配。
举个例子。
11001001
11001001
11001001
我们只看0的位置。
a
(
1
(
)
1
(
)
)
(1()1())
(1()1()).
b
(
1
)
(
1
)
(
)
(1)(1)()
(1)(1)()
我们通过观察可以发现,字符串a因为是按照0匹配的,所以肯定能最终完全匹配,b在0的位置虽然是相反的,但是可以和第一个1和最后一个1来匹配,也刚好可以完成匹配。
所以我们只需要按照0和0的匹配,1和1的匹配就可以了。
代码
#include <bits/stdc++.h>
#define ll long long
#define fi first
#define se second
#define pb push_back
#define me memset
const int N = 1e6 + 10;
const int mod = 1e9 + 7;
const int INF = 0x3f3f3f3f;
using namespace std;
typedef pair<int,int> PII;
typedef pair<ll,ll> PLL;
int main()
{
int t;
cin>>t;
while(t--)
{
int n;
cin>>n;
string s;
cin>>s;
int len=s.length();
int cnt0=0,cnt1=0;
for(int i=0 ; i<len ; i++) if(s[i]=='0') cnt0++;
cnt1=len-cnt0;
// cout<<cnt0<<" "<<cnt1<<endl;
if(cnt1%2!=0||cnt0%2!=0||s[0]!='1'||s[len-1]!='1')
{
cout<<"NO"<<endl;
continue;
}
string sa,sb;
sa+='(';
sb+='(';
cnt0=0,cnt1=0;
for(int i=1 ; i<len-1 ; i++)
{
if(s[i]=='0')
{
cnt0++;
if(cnt0%2==1)
{
sa+='(';
sb+=')';
}
else
{
sa+=')';
sb+='(';
}
}
else
{
cnt1++;
if(cnt1%2==1)
{
sa+='(';
sb+='(';
}
else
{
sa+=')';
sb+=')';
}
}
}
sa+=')';
sb+=')';
cout<<"YES"<<endl;
cout<<sa<<endl;
cout<<sb<<endl;
}
return 0;
}
总结
刚开始一直把问题想复杂了,自己的思维能力还是需要提高,这一题应该可以自己想到的。