n*m的矩阵,其中有k个格子是有图案的,q个询问,如果每次询问的两个格子上都有图案,且可以通过最多变相两次到达(路上不能有其他有图案的格子),这两个格子的图案并得到两分,否则-1分。
其实仔细想想就是连连看的游戏模式,比赛中觉得搜索太暴力会T没敢尝试,结果其实暴力写法也才80ms就过了。
直接暴力模拟能不能满足条件就可以了。
#include <iostream> #include <cstdio> #include <queue> #include <cstdlib> #include <cstring> #include <iomanip> #include <algorithm> using namespace std; const int maxn=333; int map[maxn][maxn]; int n,m; int k; int q; int ans; int x1,y1; int x2,y2; int fx[maxn],sx[maxn]; int fy[maxn],sy[maxn]; bool solve() { memset(fx,0,sizeof(fx)); memset(sx,0,sizeof(sx)); memset(fy,0,sizeof(fy)); memset(sy,0,sizeof(sy)); fx[x1]=1; sx[x2]=1; for(int i=x1+1;i<m;i++) { if(map[i][y1]==0) { fx[i]=1; } else { break; } } for(int i=x1-1;i>=0;i--) { if(map[i][y1]==0) { fx[i]=1; } else { break; } } for(int i=x2+1;i<m;i++) { if(map[i][y2]==0) { sx[i]=1; } else { break; } } for(int i=x2-1;i>=0;i--) { if(map[i][y2]==0) { sx[i]=1; } else { break; } } for(int i=0;i<m;i++) { if(sx[i]&&fx[i]) { bool flag=1; for(int j=min(y1,y2)+1;j<max(y1,y2);j++) { if(map[i][j]) { flag=0; break; } } if(flag) { return true; } } } fy[y1]=1; sy[y2]=1; for(int i=y1+1;i<n;i++) { if(map[x1][i]==0) { fy[i]=1; } else { break; } } for(int i=y1-1;i>=0;i--) { if(map[x1][i]==0) { fy[i]=1; } else { break; } } for(int i=y2+1;i<n;i++) { if(map[x2][i]==0) { sy[i]=1; } else { break; } } for(int i=y2-1;i>=0;i--) { if(map[x2][i]==0) { sy[i]=1; } else { break; } } for(int i=0;i<n;i++) { if(fy[i]&&sy[i]) { bool flag=1; for(int j=min(x1,x2)+1;j<max(x2,x1);j++) { if(map[j][i]) { flag=0; break; } } if(flag) { return true; } } } return false; } int main() { while(scanf("%d%d",&m,&n)!=EOF) { ans=60; memset(map,0,sizeof(map)); scanf("%d",&k); for(int i=0;i<k;i++) { scanf("%d%d",&x1,&y1); map[x1][y1]=1; } scanf("%d",&k); while(k--) { scanf("%d%d%d%d",&x1,&y1,&x2,&y2); if(map[x1][y1]==0||map[x2][y2]==0) { ans--; } else if(solve()) { ans+=2; map[x1][y1]=0; map[x2][y2]=0; } else { ans--; } printf("%d\n",ans); } } return 0; }
时间: 2024-10-23 23:59:46