跟POJ 1185炮兵陣地差不多
int g[16][16];int st[1001];char str[101];int dp[16][(1<<15)];int num[16][1001];int n;int tot;bool ok(int x){ if(x & (x<<1))return 0; if(x & (x>>1))return 0; return 1;}void init(){ tot = 0; int i; for(i=0;i<(1<<n);i++){ if(ok(i)){ st[tot++] = i; } }}int cal(int x,int y){ int res = 0; int i,j; int m = st[y]; int cnt =0 ; while(m){ if(m&1)res += g[x][cnt]; cnt++; m>>=1; } return res;}void gao(){ memset(dp,0,sizeof(dp)); int i,j,k; for(i=0;i<n;i++){ for(j=0;j<tot;j++){ if(!i){dp[i][j] = num[i][j];continue;} for(k=0;k<tot;k++){ if(st[j] & st[k])continue; if(st[j] & (st[k]<<1))continue; if(st[j] & (st[k]>>1))continue; dp[i][j] = max(dp[i][j], dp[i-1][k]+num[i][j]); } } } int ans = 0; for(i=0;i<tot;i++){ ans = max(ans,dp[n-1][i]); } printf("%d\n",ans);}int main(){ int i = 0,j; while(gets(str)){ n = 0; int sum = 0; for(i=0;str[i];i++){ if(str[i]==' '){ g[0][n++] = sum; sum = 0; } else { sum = sum*10+str[i]-'0'; } } g[0][n++] = sum; for(i=1;i<n;i++){ gets(str); int m = 0; sum =0 ; for(j=0;str[j];j++){ if(str[j]==' '){ g[i][m++] = sum; sum =0 ; } else { sum = sum*10+str[j]-'0'; } } g[i][m++] = sum; } init(); for(i=0;i<n;i++){ for(j=0;j<tot;j++){ num[i][j] = cal(i,j); } } gao(); getchar(); } return 0;}