题目大意:
开始的一段是介绍象棋的,不用看。题目的意思是给出一个棋盘局势,判断红方是否将死了黑方。黑方只有一个将,红方有帅、车、马、炮。
算法实现:
比较简单的模拟题,枚举黑方的将能走的位置,如果这些位置都被将军,则黑方已经被将死,否则没有。判断是否被将军的话,可以从黑方的将开始,往上、下、左、右四个方向搜索,看看是否有车或者帅直接面对它,如果没有,再隔一个棋子判断是否有炮。注意,如果隔了多个棋子炮是不能打到将的。最后再判断8个位置的马,注意蹩马腿。
参考代码:
#include <iostream>
#include <cstdio>
#include <cstring>
#define cl(xx,yy) memset((xx),(yy),sizeof((xx)))
using namespace std;
char mat[15][15];
bool solve(int x,int y)
{
bool flag=0;
for(int i=x+1;i<=10;i++)
if(mat[i][y])
{
if(!flag)
{
if(mat[i][y]=='H'||mat[i][y]=='C')
flag=1;
else
return 1;
}
else
{
if(mat[i][y]=='C')
return 1;
else
break;
}
}
flag=0;
for(int i=x-1;i>=1;i--)
if(mat[i][y])
{
if(!flag)
{
if(mat[i][y]=='H'||mat[i][y]=='C')
flag=1;
else
return 1;
}
else
{
if(mat[i][y]=='C')
return 1;
else
break;
}
}
flag=0;
for(int i=y+1;i<=10;i++)
if(mat[x][i])
{
if(!flag)
{
if(mat[x][i]=='H'||mat[x][i]=='C')
flag=1;
else
return 1;
}
else
{
if(mat[x][i]=='C')
return 1;
else
break;
}
}
flag=0;
for(int i=y-1;i>=1;i--)
if(mat[x][i])
{
if(!flag)
{
if(mat[x][i]=='H'||mat[x][i]=='C')
flag=1;
else
return 1;
}
else
{
if(mat[x][i]=='C')
return 1;
else
break;
}
}
int a[8][2]={-1,-2,-2,-1,-2,1,-1,2,1,2,2,1,2,-1,1,-2};
int b[8][2]={-1,-1,-1,-1,-1,1,-1,1,1,1,1,1,1,-1,1,-1};
for(int i=0;i<8;i++)
{
int hx=x+a[i][0],hy=y+a[i][1];
int fx=x+b[i][0],fy=y+b[i][1];
if(hx>=1&&hx<=10&&hy>=1&&hy<=10&&mat[hx][hy]=='H'&&!mat[fx][fy])
return 1;
}
return 0;
}
int main()
{
int N,x,y;
while(~scanf("%d%d%d",&N,&x,&y))
{
if(N==0&&x==0&&y==0)
break;
cl(mat,0);
for(int i=1;i<=N;i++)
{
char s[5];
int t1,t2;
scanf("%s%d%d",s,&t1,&t2);
mat[t1][t2]=s[0];
}
int dir[4][2]={1,0,-1,0,0,1,0,-1};
bool flag=1;
for(int i=0;i<4;i++)
{
int nextx=x+dir[i][0],nexty=y+dir[i][1];
if(nextx>=1&&nextx<=3&&nexty>=4&&nexty<=6)
{
if(!solve(nextx,nexty))
{
flag=0;
break;
}
}
}
if(flag)
printf("YES\n");
else
printf("NO\n");
}
return 0;
}