Xianqi UVa 1589

  这道题是一道模拟题,就是用来判断黑的一方能不能存活,所以就将黑的将军所有合法的移动情况都表示出来,看一看黑将军是否被红的将军,就可以了,主要注意的以下几点:

1、如果黑的能够直接杀死红的,那就输出 NO

2、蹩马腿的情况

3、不要越界

不过这些能够避免却仍然不能AC,为啥?下面就来聊一聊那些细节。

#include <stdio.h> 

int main() 
{
    int a = 5;
    if(a > 10) 
        if(a > 15) printf("1"); 
    else 
        printf("2");
    return 0; 
}

这个输出会是多少呢?

可能是“2”?,那你就大错特错了,不会输出任何东西,你认为else 与 第一个 if 是并列的, 然而与第二个是并列的, 将 a 的值改为 14, 输出的答案是 2 , 所以 else 只和离他最近的  if 并列,那么怎么解决这种问题呢? 打个括号就行了。

#include <stdio.h> 

int main() 
{
    int a = 5;
    if(a > 10) 
    {
        if(a > 15) printf("1"); 
    }
    else 
        printf("2");
    return 0; 
}

这样就输出“2”了,所以在写程序时一定要注意这些问题, 否则有时debug半天然后一无所获。

下面就说一说另一个问题,在读入红方的身份时,用getchar() + scanf("%c" .. 要不如 scanf("%s", s) 好, 严格来说这两种方法都行,但是面对不严谨的出题时候,用scanf(“%s", s)确实正确的,而getchar() + scanf("%c")就不行, 这道题就是这样,我们将这种情况称为鲁棒性(robustness),如果鲁棒性好的程序,会在有瑕疵数据的清狂下仍然输出正确的结果,所以写鲁棒性好的程序会加快效率,让我们得到令人惊喜的结果。

 就主要注意这两点吧!

下面是我写的代码,不长也不短,争取以后要写出短小而精悍的代码,这需要丰富我的经验与大脑。

//#define LOCAL 
#include <stdio.h> 
#include <string.h> //use memset

int chess[15][15]; 
int X, Y, B;

int G(int x, int y)
{
    for(int i = x+1; i <= 10; i++)
    {
        if(chess[i][y] == 'G'-'A') 
            return 1;
        if(chess[i][y] != 0) 
            return 0;
    }
}

int C_R(int a, int b, int x, int y, int p) //0 -> C 1 -> R 
{ 
    int cnt = 0;
    if(a == x) {
        if(b < y) {
            for(int i = b+1; i < y; i++) 
                if(chess[x][i] != 0) cnt++;
        }
        else {
            for(int i = y+1; i < b; i++)
                if(chess[x][i] != 0) cnt++;
        }
    }
    else {
        if(a < x) {
            for(int i = a+1; i < x; i++)
                if(chess[i][y] != 0) cnt++;
        }
        else {
            for(int i = x+1; i < a; i++) 
                if(chess[i][y] != 0) cnt++;
        }
    }
    if(!p) {
        if(cnt == 1) return 1; 
        return 0;
    }
    if(!cnt) return 1; 
    return 0;
}

int H(int a, int b, int x, int y)
{
    if(a+1 <= 10 && !chess[a+1][b] && ((a+2 == x && b-1 == y) || (a+2 == x && b+1 == y))) return 1;
    if(a-1 > 0 && !chess[a-1][b] && ((a-2 == x && b-1 == y) || (a-2 == x && b+1 == y))) return 1;
    if(b+1 <= 9 && !chess[a][b+1] && ((a-1 == x && b+2 == y) || (a+1 == x && b+2 == y))) return 1;
    if(b-1 > 0 && !chess[a][b-1] && ((a-1 == x && b-2 == y) || (a+1 == x && b-2 == y))) return 1;
    return 0; 
}

int Try(int x, int y) 
{
    for(int i = 1; i <= 10; i++)
        for(int j = 1; j <= 9; j++) 
            if(chess[i][j] != 0 && !(i == x && j == y)) {
                if(chess[i][j] == 'G'-'A' && j == y && G(x, y)) return 0; 
                if(chess[i][j] == 'C'-'A' && (i == x || j == y) && C_R(i, j, x, y, 0)) return 0; 
                if(chess[i][j] == 'R'-'A' && (i == x || j == y) && C_R(i, j, x, y, 1)) return 0; 
                if(chess[i][j] == 'H'-'A' && H(i, j, x, y)) return 0; 
            }
    return 1;
}

int check() 
{
    if(B == Y && G(X, Y)) return 0;
    if(X+1 < 4 && Try(X+1, Y)) return 0; 
    if(X-1 > 0 && Try(X-1, Y)) return 0;
    if(Y+1 < 7 && Try(X, Y+1)) return 0;
    if(Y-1 > 3 && Try(X, Y-1)) return 0;
    return 1;
}

int main() 
{
//    #ifdef LOCAL
//    freopen("input.txt", "r", stdin);
//    freopen("output.txt", "w", stdout); 
//    #endif
    int n, x, y;
    char a[5]; 
    while(scanf("%d%d%d", &n, &x, &y) == 3 && n != 0) {
        X = x; Y = y;
        memset(chess, 0, sizeof(chess)); 
        for(int i = 0; i < n; i++) { 
            scanf("%s%d%d", a, &x, &y); 
            if(a[0] == 'G') B = y; 
            chess[x][y] = a[0]-'A'; 
        }
        if(check()) printf("YES
"); 
        else printf("NO
"); 
    }
    return 0;
} 
语言c++计算机程序设计爱好者 不定期更新题目题解 望互相分享心得体会 有意留言加q
原文地址:https://www.cnblogs.com/yifeiWa/p/10340459.html