关于状压:可以先看我之前写的一篇
这里我们用一个数的二进制位表示的是,当前状态下患有什么病,初始化全患上
例如01011,就是 (不患,患,不患,患,患)
这里我们用到^(异或)运算符
1^1 = 0
1^0 = 1
0^0 = 0
0^1 = 1
所以每当我们取一种药的时候,就枚举这个药可以治疗的病,若& = 1,我们就与该位置^ = 0,反之若会患上该病,也是这样^ = 1,表示患上该病
代码如下:
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#include <queue>
const int maxn = 300;
using namespace std;
int n,m;
int sum;
int dist[2048];
bool inq[2048];
int cc[maxn][maxn];
inline int read()
{
int f = 1;
int data = 0;
char ch;
while(ch < '0'||ch > '9')
{
ch = getchar();
if(ch == '-') f = -1;
}
do {
data = data*10 + ch-'0';
ch = getchar();
}while(ch >= '0'&&ch <= '9');
return f*data;
}
queue<int >q;
inline void bfs(int x)
{
memset(dist,0,sizeof(dist));
memset(inq,0,sizeof(inq));
q.push(x);
inq[x] = 1;
dist[x] = 0;
while(!q.empty())
{
int now = q.front();
q.pop();
for(int i = 1;i <= m;i++)
{
int k = now;
for(int j = 0;j < n;j++)
{
if(cc[i][j] == 1) {if(k&(1 << j)) k = k^(1 << j);}
else if(cc[i][j] == -1) {if(!(k&(1 << j))) k = k^(1 << j);}
}
//cout<<k<<endl;
//cout<<"dist of k is "<<dist[k]<<endl;
if(!inq[k])
{
dist[k] = dist[now]+1;
inq[k] = 1;
q.push(k);
}
//cout<<k<<endl;
if(k == 0)
{
printf("%d\n",dist[k]);
exit(0) ;
}
}
}
printf("The patient will be dead.\n");
return ;
}
int main()
{
n = read();
m = read();
for(int i = 1;i <= m;i++)
for(int j = 0;j < n;j++)
cc[i][j] = read();
//cout<<(1 << n)-1<<endl;
bfs((1 << n)-1);
return 0;
}
THE END
By Peacefuldoge