在tic-tac-toe实现中减少代码重复

时间:2017-12-17 12:24:24

标签: c

我在C中制作一个井字游戏,我的函数checkwinner()以if语句的形式有很多代码重复。

void checkwinner(void){
     if(square[1] == square[2] && square[2] == square[3]){
         printresult(square[2]);
     }
     else if(square[4] == square[5] && square[5] == square[6]){
         printresult(square[5]);
     }
     else if(square[7] == square[8] && square[8] == square[9]){
         printresult(square[8]);
     }
     else if(square[1] == square[4] && square[4] == square[7]){
         printresult(square[4]);
     }
     else if(square[2] == square[5] && square[5] == square[8]){
         printresult(square[5]);
     }
     else if(square[3] == square[6] && square[6] == square[9]){
         printresult(square[6]);
     }
     else if(square[1] == square[5] && square[5] == square[9]){
         printresult(square[5]);
     }
     else if(square[3] == square[5] && square[5] == square[7]){
         printresult(square[5]);
     }
}

名为square []的数组包含字符“X”或“O”。因此该函数比较行,列和对角线,并检查字符是否匹配。

有没有办法减少代码重复以使代码更紧凑?

2 个答案:

答案 0 :(得分:1)

就像Angen所说,匹配功能很好:

bool match(int x, int y, int z){
    return square[x] == square[y] && square[y] == square[z];
}

但是,我也会考虑像这样重写。我假设您的squarechar数组,但它也适用于int。另请注意,您需要检查空单元格。

/* Returns the winner on match, and otherwise 0 */
char match(int x, int y, int z){
    if(square[x] != 'X' && square[x] != 'O')
        return 0;
    if (square[x] == square[y] && square[y] == square[z])
        return square[x];
    returns 0;
}

之后,您可以分别检查三个案例。也许这对于一个小小的tic tac toe来说太过分了,但无论如何我都会表现出来。这个想法很好地转化为更大的应用程序。

char matchRows() {
    int row=1;
    for(int i=0; i<3; i++) {
         char c=match(row+i, row+3+i, row+6+i);
         if(c)
             return c;
    }
    return 0;
}

char matchColumns() {
    int column=1;
    for(int i=0; i<3; i++) {
         char c=match(column+i, column+1+i, column+2+i);
         if(c)
             return c;
    }
    return 0;
}

char matchDiagonals() {
    char c;
    if(c=match(1,5,9))
        return c;
    if(c=match(3,5,7))
        return c;
    return 0;
}

然后你可以像这样写checkwinner

char checkWinner() {
    char c;
    if(c=matchRows()) 
        return c;
    if(c=matchColumns()) 
        return c;
    if(c=matchDiagonals())
        return c;
    return c;            
}

然后我会添加一个新函数来接管前一个checkWinner的职责:

void printWinner() {
    char c=checkWinner();
    if(c)
        printResult(c);
}

在计算总行数时,这可能不会使代码更紧凑,但它绝对是更好的设计,每个单独的功能都更紧凑。另外,正如您可能注意到的那样,我将功能分开,这样功能就不会打印和处理有关如何计算胜利者的逻辑。

我在您的功能中添加了camelCase。这使代码更容易阅读。

答案 1 :(得分:0)

你可以写这样的功能

url = "http://centrebet.com/"
current_url = driver.current_url # http://centrebet.com/Sports/12313443
new_url = current_url.replace(url, url + "#") # http://centrebet.com/#Sports/12313443 

然后

bool match(int x, int y, int z){
    return square[x] == square[y] && square[y] == square[z];
}

您可以将printresult移动到匹配功能

void checkwinner(void){
         if(match(1,2,3)){
         printresult(square[2]);
         }
         else if(match(4,5,6)){
         printresult(square[5]);
         } ... 

然后就像你的功能没有别的事情那样

bool match(int x, int y, int z){
        if(square[x] == square[y] && square[y] == square[z]){
             printresult(square[y]);
              return true;
        }
    return false;
    }