题目:
题意:
同POJ1222,如果有多解,输出修改点数最少的,如果无解,输出inf
题解:
和POJ1222很类似,只需要再判断多解和无解的情况
如果出现自由元的话
如果b为0,那么就是有多解,因为除了第i位别的全都没了,自由元意味着系数为0了,0*x=0,那么x取1/0都可以,因为点数要求最少,直接是0就好咯
如果b=1就是无解
1A啦
代码:
#include <cstdio>
#include <bitset>
#include <cstring>
using namespace std;
bitset <250> a[250];
int n,b[250],s[20][20];bool flag[250];
char st[20];
void gauss()
{
int ans=0;
for (int i=1;i<=n;i++)
{
if (a[i][i]==0)
{
int num=i;
for (int j=i+1;j<=n;j++)
if (a[j][i]) {num=j; break;}
if (num==i) {flag[i]=1;continue;}
swap(a[i],a[num]); swap(b[i],b[num]);
}
for (int j=i+1;j<=n;j++)
if (a[j][i]) a[j]^=a[i],b[j]^=b[i];
}
for (int i=n;i>=1;i--)
{
if (flag[i])
{
if (b[i]==0) continue;
else {printf("inf\n");return;}
}
ans+=b[i];
for (int j=1;j<i;j++)
if (a[j][i]) b[j]^=b[i];
}
printf("%d\n",ans);
}
int main()
{
int T;scanf("%d",&T);
while (T--)
{
memset(a,0,sizeof(a));
memset(flag,0,sizeof(flag));
scanf("%d",&n);
for (int i=1;i<=n;i++)
{
scanf("%s",st+1);
for (int j=1;j<=n;j++)
if (st[j]=='y') s[i][j]=0;else s[i][j]=1;
}
for (int i=1;i<=n;i++)
for (int j=1;j<=n;j++)
{
int t=(i-1)*n+j;
a[t][t]=1;
if (i!=1) a[t][t-n]=1;
if (i!=n) a[t][t+n]=1;
if (j!=1) a[t][t-1]=1;
if (j!=n) a[t][t+1]=1;
if (s[i][j]) b[t]=1;else b[t]=0;
}
n=n*n;
gauss();
}
}