状压DP
本来如果考虑所有情况应该开hh[n][2^10][2^10]表示i行在i-1的状态为j,i-2的状态为k的最大个数
但是由于每行中的人互相限制所以在m=10时只有60种情况
空间就可以满足,时间也可以满足了
1 #include<algorithm> 2 #include<iostream> 3 #include<cstdlib> 4 #include<cstring> 5 #include<cstdio> 6 #include<string> 7 #include<cmath> 8 #include<ctime> 9 #include<queue> 10 #include<stack> 11 #include<map> 12 #include<set> 13 #define rre(i,r,l) for(int i=(r);i>=(l);i--) 14 #define re(i,l,r) for(int i=(l);i<=(r);i++) 15 #define Clear(a,b) memset(a,b,sizeof(a)) 16 #define inout(x) printf("%d",(x)) 17 #define douin(x) scanf("%lf",&x) 18 #define strin(x) scanf("%s",(x)) 19 #define LLin(x) scanf("%lld",&x) 20 #define op operator 21 #define CSC main 22 typedef unsigned long long ULL; 23 typedef const int cint; 24 typedef long long LL; 25 using namespace std; 26 void inin(int &ret) 27 { 28 ret=0;int f=0;char ch=getchar(); 29 while(ch<'0'||ch>'9'){if(ch=='-')f=1;ch=getchar();} 30 while(ch>='0'&&ch<='9')ret*=10,ret+=ch-'0',ch=getchar(); 31 ret=f?-ret:ret; 32 } 33 int s[66],x,shu[66]; 34 int n,m,a[111]; 35 int hh[111][66][66]; 36 char ss[111][11]; 37 void dfs(int xx,int ss,int sh) 38 { 39 if(xx>m) 40 { 41 s[++x]=ss;shu[x]=sh; 42 return ; 43 } 44 dfs(xx+1,ss,sh); 45 dfs(xx+3,ss|(1<<xx),sh+1); 46 } 47 int CSC() 48 { 49 freopen("in.in","r",stdin); 50 freopen("out.out","w",stdout); 51 inin(n),inin(m); 52 dfs(1,0,0); 53 re(i,1,n) 54 { 55 strin(ss[i]+1); 56 re(j,1,m)if(ss[i][j]=='H')a[i]|=(1<<j); 57 } 58 re(i,1,x)if(!(a[1]&s[i])) 59 hh[1][i][0]=shu[i]; 60 re(i,1,x) 61 if(!(a[2]&s[i])) 62 re(j,1,x) 63 if(!(s[i]&s[j])) 64 hh[2][i][j]=max(hh[2][i][j],hh[1][j][0]+shu[i]); 65 re(r,3,n) 66 re(i,1,x)if(!(s[i]&a[r])) 67 re(j,1,x)if(!(s[j]&a[r-1]))if(!(s[i]&s[j])) 68 re(k,1,x)if(!(s[k]&a[r-2]))if(!(s[j]&s[k]))if(!(s[i]&s[k])) 69 hh[r][i][j]=max(hh[r][i][j],hh[r-1][j][k]+shu[i]); 70 int ans=0; 71 re(i,1,x)re(j,1,x) 72 ans=max(ans,hh[n][i][j]); 73 printf("%d",ans); 74 return 0; 75 }