12996 - Reversi   

Description

“黑白棋”是一種雙人對弈的棋類遊戲。棋盤共有8行8列共64格。開局時,棋盤正中央的4格先置放黑白相隔的4枚棋子。雙方輪流落子。只要落子和棋盤上任一枚己方的棋子在一條線上(橫、直、斜線皆可)夾著對方棋子,就能將對方的這些棋子轉變為我己方。不能在不能夾住對手的任一顆棋子的地方落子。遊戲在雙方都不能再落子,或棋盤已無空格的情況下結束,子多的一方勝。

給定一個棋局,以及黑方或白方下一個落子的位置,請試著模擬出落子後棋局的變化。請利用最後附上的 main.c,並完成未完成的函式CreateBoard()UpdateBoardInDir()

 

Note:

  1. 利用字元 ‘_’ 來代表棋盤中的空格
  2. 利用字元 ‘x’ 來代表棋盤中的黑子
  3. 利用字元 ‘o’ 來代表棋盤中的白子
  4. 字元之間存在著空格將其分開

舉例:

- 給定的棋局範例

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

_ _ _ o x _ _ _

_ _ _ x x x _ _

_ _ _ _ x o _ _

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

 

- 白子落在(5, 3)後的棋局變化

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

_ _ _ o x _ _ _

_ _ _ o x x _ _

_ _ _ o o o _ _

_ _ _ _ _ _ _ _

_ _ _ _ _ _ _ _

 

main.c

#include <stdio.h>
 
static int row = 8, col = 8;
 
void CreateBoard(char arr[row][col]);
void PlaceStone(char arr[row][col]);
void UpdateBoardInDir(char self, char opnt, int r, int c, int r_step, int c_step, char arr[row][col]);
void PrintBoard(char arr[row][col]);
 
int main()
{
    char board[row][col];
    CreateBoard(board);
    PlaceStone(board);
    PrintBoard(board);
    return 0;
}
 
void CreateBoard(char arr[row][col])
{
 
    for (int i = 0; i < row; i++)
    {
        for (int j = 0; j < col;)
        {
            char c;
            scanf("%c", &c);
            if (c == 'x' || c == 'o' || c == '_')
            {
                /* Todo */
                // .....
                j++;
            }
        }
    }
}
 
void PlaceStone(char arr[row][col])
{
    // turn: whose turn to play
    // self: the color of stone I hold
    // opnt: the color of stone my oponent holds
    char turn, self, opnt;
 
    int r, c;
    scanf(" %c %d %d", &turn, &r, &c);
 
    if (turn == 'x')
    {
        self = 'x';
        opnt = 'o';
    }
    else
    {
        self = 'o';
        opnt = 'x';
    }
    arr[r][c] = self;
 
    // check 8 directions
    for (int i = -1; i <= 1; i++)
    {
        for (int j = -1; j <= 1; j++)
        {
            if (i == 0 && j == 0)
                continue;
 
            UpdateBoardInDir(self, opnt, r, c, i, j, arr);
        }
    }
}
 
void UpdateBoardInDir(char self, char opnt, int r, int c, int r_step, int c_step, char arr[row][col])
{
    // has_self:    代表最後有遇到跟自己同樣顏色的棋子
    // count_opnt:  代表總共經過多少顆敵方的棋子
    int has_self = 0, count_opnt = 0;
 
    // Check
    for (int i = r + r_step, j = c + c_step; i < row && i > -1 && j < col && j > -1; i = i + r_step, j = j + c_step)
    {
        if (arr[i][j] == '_')
        {
            /* Todo */
            // .....
        }
        else if (arr[i][j] == opnt)
        {
            /* Todo */
            // .....
        }
        else if (arr[i][j] == self)
        {
            /* Todo */
            // .....
        }
    }
 
    // Update
    if (has_self && count_opnt)
    {
        for (int i = r + r_step, j = c + c_step, k = 0; k < count_opnt; i = i + r_step, j = j + c_step, k++)
        {
            arr[i][j] = self;
        }
    }
}
 
void PrintBoard(char arr[row][col])
{
    for (int i = 0; i < row; i++)
    {
        printf("%c", arr[i][0]);
        for (int j = 1; j < col; j++)
        {
            printf(" %c", arr[i][j]);
        }
        printf("\n");
    }
}

Input

一個棋局;一個字元用來表示現在是黑方或白方落子;兩個整數用來表示落子的位置。

 

Note:

  1. ‘x’ 表示現在為黑方落子;‘o’ 表示現在為白方落子
  2. 測資中不會出現不合遊戲規則的落子位置

Output

落子後的棋局

輸出比須符合以下格式:

c c c c c c c c

c c c c c c c c

c c c c c c c c

c c c c c c c c

c c c c c c c c

c c c c c c c c

c c c c c c c c

c c c c c c c c

 

Note:

  1. 輸出的最後必須要有一個換行符號 ('\n')
  2. 字元 c‘_’‘x’‘o’ 中一種

Sample Input  Download

Sample Output  Download

Tags




Discuss