简单构造题。
首先转化为有
x
x
x个人左右都是男生,
y
y
y个人左右都是女生。接着可以发现这相当于隔
2
2
2个位置的人之间,有
x
x
x组都是男生,
y
y
y组都是女生。
先考虑另一个问题:一个长为
n
n
n的环,有
x
x
x对相邻的人都是男生,
y
y
y对相邻的人都是女生,问有解条件。显然需要满足
x
+
y
≤
n
x+y\leq n
x+y≤n且与
n
n
n奇偶性相同,且
x
+
y
=
n
x+y=n
x+y=n的话当且仅当
x
=
n
x=n
x=n或
y
=
n
y=n
y=n时有解(全为男生或全为女生)。如果
x
+
y
≤
n
−
2
x+y\leq n-2
x+y≤n−2且与
n
n
n奇偶性相同,那么先安排
x
+
1
x+1
x+1个男生,再安排
y
+
1
y+1
y+1个女生,后面男女生交替即可。
现在如果
n
n
n是奇数,容易重标号得到上面的问题。
n
n
n是偶数的话相当于有两个长为
n
2
\frac{n}{2}
2n的环,比较简单的处理是枚举在第一个环上相邻男生的对数(
≤
x
\leq x
≤x),显然接下来会在奇偶性满足条件的前提下,尽可能最大化第一个环上相邻女生的对数(
≤
y
\leq y
≤y),这样也可以知道另一个环的情况了。
时间复杂度为
O
(
n
)
\mathcal O(n)
O(n)。
#include <bits/stdc++.h>
using namespace std;
char ans[100005];
int main() {
freopen("boysgirls.in","r",stdin);
freopen("boysgirls.out","w",stdout);
int n,x,y;
scanf("%d%d%d",&n,&x,&y);
x=n-x;y=n-y;
swap(x,y);
/*if (n==2) {
if (x+y!=2) {
puts("Impossible");
return 0;
}
for(int i=1;i<=x;i++) putchar('B');
for(int i=1;i<=y;i++) putchar('G');
printf("\n");
return 0;
}*/
if (n&1) {
if (!((x+y)&1)) {
puts("Impossible");
return 0;
}
if (!x&&y==n) {
for(int i=1;i<=n;i++) putchar('G');
printf("\n");
return 0;
}
if (!y&&x==n) {
for(int i=1;i<=n;i++) putchar('B');
printf("\n");
return 0;
}
if (x+y>=n) {
puts("Impossible");
return 0;
}
for(int i=1;i<=x+1;i++) ans[(2*i-1)%n+1]='B';
for(int i=1;i<=y+1;i++) ans[(2*(x+1+i)-1)%n+1]='G';
for(int i=1;i<=n-x-y-2;i++) ans[(2*(x+y+2+i)-1)%n+1]=((i&1)?'B':'G');
puts(ans+1);
}
else {
if ((x+y)&1) {
puts("Impossible");
return 0;
}
if (!x&&y==n) {
for(int i=1;i<=n;i++) putchar('G');
printf("\n");
return 0;
}
if (!y&&x==n) {
for(int i=1;i<=n;i++) putchar('B');
printf("\n");
return 0;
}
for(int i=0;i<=min(n/2,x);i++) {
int j=min(y,max(0,n/2-i-2));
if (((i+j)^(n/2))&1) {
if (!j) continue;
else j--;
}
int u=x-i,v=y-j;
if (u+v>n/2||(u+v==n/2&&u&&v)) continue;
if (i==n/2) {
for(int k=1;k<=n/2;k++) ans[2*k]='B';
}
else if (j==n/2) {
for(int k=1;k<=n/2;k++) ans[2*k]='G';
}
else {
for(int k=1;k<=i+1;k++) ans[2*k]='B';
for(int k=1;k<=j+1;k++) ans[2*(i+1+k)]='G';
for(int k=1;k<=n/2-i-j-2;k++) ans[2*(i+j+2+k)]=((k&1)?'B':'G');
}
if (u==n/2) {
for(int k=1;k<=n/2;k++) ans[2*k-1]='B';
}
else if (v==n/2) {
for(int k=1;k<=n/2;k++) ans[2*k-1]='G';
}
else {
for(int k=1;k<=u+1;k++) ans[2*k-1]='B';
for(int k=1;k<=v+1;k++) ans[2*(u+1+k)-1]='G';
for(int k=1;k<=n/2-u-v-2;k++) ans[2*(u+v+2+k)-1]=((k&1)?'B':'G');
}
puts(ans+1);
return 0;
}
puts("Impossible");
}
return 0;
}