三目並べ #3
冗長だったのでもっといい加減に。
3x3以外の枡、それはもはや三目並べではない。
不正入力に対してもう少しマシな動作に。
#include <stdio.h> typedef enum { EMPTY, WHITE, BLACK, DRAW } side; static void init(void); static void show(void); static char expr(int i); static int input(void); static int validate(int c); static side judge(int p); static side grid[9]; static side turn; static const char symbol[] = {' ', 'O', 'X', '?'}; static const char esymbol[] = {'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'}; int main(void) { int c, p; side winner = EMPTY; init(); for (;;) { printf("%c's turn\n", symbol[turn]); show(); fputs("where do you put? ", stdout); if ((p = validate(c = input())) >= 0) { winner = judge(p); if (winner != EMPTY) break; if (turn == WHITE) turn = BLACK; else turn = WHITE; } else { printf("invalid input: %c\n", c); } } show(); if (winner == DRAW) { puts("draw game"); } else { printf("winner is %c\n", symbol[winner]); } return 0; } static void init(void) { int i; for (i = 0; i < 9; i++) grid[i] = EMPTY; turn = WHITE; } static void show(void) { printf("%c|%c|%c\n", expr(0), expr(1), expr(2)); puts("-+-+-"); printf("%c|%c|%c\n", expr(3), expr(4), expr(5)); puts("-+-+-"); printf("%c|%c|%c\n", expr(6), expr(7), expr(8)); } static char expr(int i) { return grid[i] == EMPTY ? esymbol[i] : symbol[grid[i]]; } static int input(void) { int c = getchar(), d = c; while (d != '\n') d = getchar(); return c; } static int validate(int c) { int i; for (i = 0; i < 9; i++) { if (esymbol[i] == c && grid[i] == EMPTY) { grid[i] = turn; return i; } } return -1; } static side judge(int p) { static const int line[][3] = { {0, 1, 2}, {3, 4, 5}, {6, 7, 8}, {0, 3, 6}, {1, 4, 7}, {2, 5, 8}, {0, 4, 8}, {2, 4, 6} }; static const int pos[][5] = { {0, 3, 6, -1, 0}, {0, 4, -1, 0, 0}, {0, 5, 7, -1, 0}, {1, 3, -1, 0, 0}, {1, 4, 6, 7, -1}, {1, 5, -1, 0, 0}, {2, 3, 7, -1, 0}, {2, 4, -1, 0, 0}, {2, 5, 6, -1, 0} }; int i; side g; for (i = 0; pos[p][i] >= 0; i++) { const int *l = line[pos[p][i]]; if ((g = grid[l[0]]) == turn && g == grid[l[1]] && g == grid[l[2]]) return turn; } for (i = 0; i < 9; i++) if (grid[i] == EMPTY) return EMPTY; return DRAW; }