Compare commits
No commits in common. "87e7ff5829a8c0f012c4ed052a3d9568d4b8a548" and "83df11530c3d079965a2d1f8d916d1ed14a9c9d1" have entirely different histories.
87e7ff5829
...
83df11530c
7 changed files with 39 additions and 158 deletions
|
@ -24,9 +24,4 @@ typedef enum {
|
||||||
ALMOST,
|
ALMOST,
|
||||||
} e_status;
|
} e_status;
|
||||||
|
|
||||||
typedef enum {
|
|
||||||
HUMAN,
|
|
||||||
RANDOM,
|
|
||||||
CLEVER,
|
|
||||||
} e_tactic;
|
|
||||||
#endif /*COMMON*/
|
#endif /*COMMON*/
|
||||||
|
|
17
include/ia.h
17
include/ia.h
|
@ -1,17 +0,0 @@
|
||||||
#ifndef IA_H
|
|
||||||
#define IA_H
|
|
||||||
#include "common.h"
|
|
||||||
#include "model.h"
|
|
||||||
/*!
|
|
||||||
* This function modify the move in parameter in order to get a valid move (1) randomly if tactic is 0 or
|
|
||||||
* (2) in a clever way if tactic is 1 in the corresponding utictactoe u.
|
|
||||||
*
|
|
||||||
* \param p_uttt a pointer on a s_utictactoe.
|
|
||||||
* \param p_move a pointer on a s_move to be modified.
|
|
||||||
* \param tactic an e_tactic set to 0 for random strategy and 1 for clever one.
|
|
||||||
*/
|
|
||||||
void best_move(s_utictactoe* p_uttt, s_move* p_move, e_tactic tactic);
|
|
||||||
|
|
||||||
s_tictactoe * clone_ttt( s_tictactoe * p_ttt );
|
|
||||||
e_location get_best_random_position( s_tictactoe * p_uttt, e_player player);
|
|
||||||
#endif
|
|
|
@ -25,9 +25,8 @@ int elocation_to_coord(e_location l);
|
||||||
* \param p_move a pointer on a s_move to be modified.
|
* \param p_move a pointer on a s_move to be modified.
|
||||||
* \param v a pointer on the view to use.
|
* \param v a pointer on the view to use.
|
||||||
*/
|
*/
|
||||||
void set_next_player_move(s_move * p_move, p_view v, e_tactic tactic);
|
void set_next_player_move(s_move * p_move, p_view v);
|
||||||
|
|
||||||
void display_winner(p_view v);
|
|
||||||
/*!
|
/*!
|
||||||
* This function free all the memory used by a given view which
|
* This function free all the memory used by a given view which
|
||||||
* reference is given.
|
* reference is given.
|
||||||
|
|
|
@ -3,4 +3,4 @@ set(CMAKE_C_FLAGS "-std=c99 -lncurses -g -Wall")
|
||||||
set(CMAKE_INSTALL_PREFIX ".")
|
set(CMAKE_INSTALL_PREFIX ".")
|
||||||
include_directories(../include)
|
include_directories(../include)
|
||||||
project(utictactoe)
|
project(utictactoe)
|
||||||
add_executable(${PROJECT_NAME} utictactoe.c model.c view.c ia.c)
|
add_executable(${PROJECT_NAME} utictactoe.c model.c view.c)
|
||||||
|
|
76
src/ia.c
76
src/ia.c
|
@ -1,76 +0,0 @@
|
||||||
#include "common.h"
|
|
||||||
#include "model.h"
|
|
||||||
#include "view.h"
|
|
||||||
#include "ia.h"
|
|
||||||
|
|
||||||
void best_move (s_utictactoe * p_uttt, s_move * m ,e_tactic tactic)
|
|
||||||
{
|
|
||||||
//do{
|
|
||||||
if ( p_uttt->inception_level == 1 ) {
|
|
||||||
m->outer_position = get_best_random_position(
|
|
||||||
p_uttt->outer_tictactoe,
|
|
||||||
m->player
|
|
||||||
);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m->outer_position = get_next_outer_position(p_uttt);
|
|
||||||
if ( m->outer_position == FREE ) {
|
|
||||||
do {
|
|
||||||
m->outer_position = (e_location)(TOPLEFT + rand() % TICTACTOE_SIZE);
|
|
||||||
} while(p_uttt->inner_tictactoes[m->outer_position]->winner != NOBODY);
|
|
||||||
}
|
|
||||||
|
|
||||||
m->inner_position = get_best_random_position(
|
|
||||||
p_uttt->inner_tictactoes[m->outer_position],
|
|
||||||
m->player
|
|
||||||
);
|
|
||||||
}
|
|
||||||
//} while (is_move_valid(p_uttt,m) != YES);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
s_tictactoe * clone_ttt( s_tictactoe * p_ttt ) {
|
|
||||||
s_tictactoe * t = create_empty_tictactoe();
|
|
||||||
for (int i=0; i<TICTACTOE_SIZE; i++){
|
|
||||||
t->content[i] = p_ttt->content[i];
|
|
||||||
}
|
|
||||||
return t;
|
|
||||||
}
|
|
||||||
|
|
||||||
e_location get_best_random_position (s_tictactoe * p_ttt, e_player player) {
|
|
||||||
mvwprintw(stdscr, 13, 0, " ");
|
|
||||||
s_tictactoe * c_ttt = clone_ttt(p_ttt);
|
|
||||||
e_player opponent = ( player == PLAYER_O )?PLAYER_X:PLAYER_O;
|
|
||||||
|
|
||||||
// Check if IA player can win
|
|
||||||
for(int i=0; i<TICTACTOE_SIZE; i++) {
|
|
||||||
if(c_ttt->content[i] == NOBODY) {
|
|
||||||
c_ttt->content[i] = player;
|
|
||||||
set_tictactoe_winner(c_ttt);
|
|
||||||
if ( c_ttt->winner != NOBODY ) {
|
|
||||||
free_tictactoe(c_ttt);
|
|
||||||
mvwprintw(stdscr, 13, 0, "Je vais gagner ");
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
c_ttt->content[i] = NOBODY;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// avoid loosing
|
|
||||||
for(int i=0; i<TICTACTOE_SIZE; i++) {
|
|
||||||
if(c_ttt->content[i] == NOBODY) {
|
|
||||||
c_ttt->content[i] = opponent;
|
|
||||||
set_tictactoe_winner(c_ttt);
|
|
||||||
if ( c_ttt->winner != NOBODY ) {
|
|
||||||
free_tictactoe(c_ttt);
|
|
||||||
mvwprintw(stdscr, 13, 0, "Je ne peux pas te laisser gagner!");
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
c_ttt->content[i] = NOBODY;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// We have not a winnner move...
|
|
||||||
free_tictactoe(c_ttt);
|
|
||||||
return (e_location)(rand() % TICTACTOE_SIZE);
|
|
||||||
}
|
|
|
@ -9,7 +9,6 @@
|
||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "model.h"
|
#include "model.h"
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "ia.h"
|
|
||||||
|
|
||||||
#define OPTIONAL_ARGUMENT_IS_PRESENT \
|
#define OPTIONAL_ARGUMENT_IS_PRESENT \
|
||||||
((optarg == NULL && optind < argc && argv[optind][0] != '-') \
|
((optarg == NULL && optind < argc && argv[optind][0] != '-') \
|
||||||
|
@ -47,15 +46,15 @@ int check_int_value ( char *value, int min, int max){
|
||||||
|
|
||||||
int main(int argc, char* argv[]) {
|
int main(int argc, char* argv[]) {
|
||||||
int optc;
|
int optc;
|
||||||
e_tactic tactic_cross = HUMAN, tactic_round = HUMAN;
|
int cross_ai, round_ai = 0;
|
||||||
int inception_level = 2;
|
int inception_level = 0;
|
||||||
bool verbose, contest_mode = false;
|
bool verbose, contest_mode = false;
|
||||||
char * contest_file;
|
char * contest_file;
|
||||||
static struct option long_opts[] =
|
static struct option long_opts[] =
|
||||||
{
|
{
|
||||||
{"inception-level", optional_argument, 0, 'i'},
|
{"inception-level", optional_argument, 0, 'i'},
|
||||||
{"tactic_cross", required_argument, 0, 'x'},
|
{"cross-ai", required_argument, 0, 'x'},
|
||||||
{"tactic_round", required_argument, 0, 'o'},
|
{"round-ai", required_argument, 0, 'o'},
|
||||||
{"contest", required_argument, 0, 'c'},
|
{"contest", required_argument, 0, 'c'},
|
||||||
{"verbose", no_argument, 0, 'v'},
|
{"verbose", no_argument, 0, 'v'},
|
||||||
{"version", no_argument, 0, 'V'},
|
{"version", no_argument, 0, 'V'},
|
||||||
|
@ -81,8 +80,8 @@ int main(int argc, char* argv[]) {
|
||||||
case 'x':
|
case 'x':
|
||||||
printf ("cross ai\n");
|
printf ("cross ai\n");
|
||||||
if ( optarg ) {
|
if ( optarg ) {
|
||||||
tactic_cross = check_int_value(optarg, 0, 2);
|
cross_ai = check_int_value(optarg, 0, 1);
|
||||||
if ( tactic_cross == -1 ) {
|
if ( cross_ai == -1 ) {
|
||||||
fprintf(stderr, "Error: incorrect cross ai value\n");
|
fprintf(stderr, "Error: incorrect cross ai value\n");
|
||||||
exit (EXIT_FAILURE);
|
exit (EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
@ -97,8 +96,8 @@ int main(int argc, char* argv[]) {
|
||||||
case 'o':
|
case 'o':
|
||||||
printf ("round ai\n");
|
printf ("round ai\n");
|
||||||
if ( optarg ) {
|
if ( optarg ) {
|
||||||
tactic_round = check_int_value(optarg, 0, 2);
|
round_ai = check_int_value(optarg, 0, 1);
|
||||||
if ( tactic_round == -1 ) {
|
if ( round_ai == -1 ) {
|
||||||
fprintf(stderr, "Error: incorrect round ai value\n");
|
fprintf(stderr, "Error: incorrect round ai value\n");
|
||||||
exit (EXIT_FAILURE);
|
exit (EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
|
@ -142,23 +141,35 @@ int main(int argc, char* argv[]) {
|
||||||
exit (EXIT_FAILURE);
|
exit (EXIT_FAILURE);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
srand(time(NULL));
|
s_utictactoe *s = create_empty_utictactoe(1);
|
||||||
s_utictactoe *s = create_empty_utictactoe(inception_level);
|
|
||||||
s_move *m = create_empty_move();
|
s_move *m = create_empty_move();
|
||||||
p_view v = create_view(s);
|
p_view v = create_view(s);
|
||||||
while (s->outer_tictactoe->winner == NOBODY) {
|
while (s->outer_tictactoe->winner == NOBODY) {
|
||||||
m->player = get_next_player_to_play(s);
|
m->player = get_next_player_to_play(s);
|
||||||
m->outer_position = get_next_outer_position(s);
|
m->outer_position=get_next_outer_position(s);
|
||||||
if (m->player == PLAYER_X) {
|
set_next_player_move(m,v);
|
||||||
set_next_player_move(m, v, tactic_cross);
|
|
||||||
} else {
|
|
||||||
set_next_player_move(m, v, tactic_round);
|
|
||||||
}
|
|
||||||
play_move(s, m);
|
play_move(s, m);
|
||||||
}
|
}
|
||||||
display_winner(v);
|
|
||||||
getchar();//just to pause before quitting the program
|
|
||||||
free_view(v);
|
free_view(v);
|
||||||
|
draw_utictactoe(s);
|
||||||
|
draw_utictactoe_history(s);
|
||||||
|
printf("The winner is : %c\n", s->outer_tictactoe->winner);
|
||||||
|
free_move(m);
|
||||||
|
free_utictactoe(s);
|
||||||
|
|
||||||
|
s = create_empty_utictactoe(2);
|
||||||
|
m = create_empty_move();
|
||||||
|
v = create_view(s);
|
||||||
|
while (s->outer_tictactoe->winner == NOBODY) {
|
||||||
|
m->player = get_next_player_to_play(s);
|
||||||
|
m->outer_position=get_next_outer_position(s);
|
||||||
|
set_next_player_move(m,v);
|
||||||
|
play_move(s, m);
|
||||||
|
m->outer_position = m->inner_position;
|
||||||
|
}
|
||||||
|
free_view(v);
|
||||||
|
draw_utictactoe_history(s);
|
||||||
|
printf("The winner is : %c\n", s->outer_tictactoe->winner);
|
||||||
free_move(m);
|
free_move(m);
|
||||||
free_utictactoe(s);
|
free_utictactoe(s);
|
||||||
}
|
}
|
||||||
|
|
37
src/view.c
37
src/view.c
|
@ -1,7 +1,6 @@
|
||||||
#include "common.h"
|
#include "common.h"
|
||||||
#include "model.h"
|
#include "model.h"
|
||||||
#include "view.h"
|
#include "view.h"
|
||||||
#include "ia.h"
|
|
||||||
|
|
||||||
struct view{
|
struct view{
|
||||||
s_utictactoe * p_uttt;
|
s_utictactoe * p_uttt;
|
||||||
|
@ -67,15 +66,8 @@ void draw_ttt(WINDOW * w, s_tictactoe * u){
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void set_next_player_move(s_move * m, p_view v, e_tactic tactic )
|
void set_next_player_move(s_move * m, p_view v)
|
||||||
{
|
{
|
||||||
|
|
||||||
// computer player
|
|
||||||
if(tactic != HUMAN) {
|
|
||||||
best_move(v->p_uttt, m, tactic);
|
|
||||||
return ;
|
|
||||||
}
|
|
||||||
|
|
||||||
char * s="Player to play:%c";
|
char * s="Player to play:%c";
|
||||||
int in_x = 3, out_x = 3;
|
int in_x = 3, out_x = 3;
|
||||||
int out_y = 2, in_y = 2;
|
int out_y = 2, in_y = 2;
|
||||||
|
@ -136,17 +128,7 @@ void set_next_player_move(s_move * m, p_view v, e_tactic tactic )
|
||||||
case KEY_BACKSPACE:
|
case KEY_BACKSPACE:
|
||||||
case 127:
|
case 127:
|
||||||
case '\b':
|
case '\b':
|
||||||
// if we are in inner TTT window, go back to outer
|
|
||||||
if ( outer_selected == true && v->p_uttt->inception_level == 2 ) {
|
|
||||||
outer_selected = false;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
// If not Exit programm, but we need to do it properly.
|
|
||||||
free_utictactoe(v->p_uttt);
|
|
||||||
free_move(m);
|
|
||||||
free_view(v);
|
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
|
||||||
break;
|
break;
|
||||||
case KEY_RIGHT:
|
case KEY_RIGHT:
|
||||||
if ( outer_selected ) {
|
if ( outer_selected ) {
|
||||||
|
@ -250,24 +232,11 @@ int elocation_to_coord(e_location l){
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void display_winner(p_view v){
|
|
||||||
int ch = ' ';
|
|
||||||
draw_ttt(v->w_uttt, v->p_uttt->outer_tictactoe);
|
|
||||||
wrefresh(v->w_uttt);
|
|
||||||
if (v->p_uttt->inception_level == 2){
|
|
||||||
draw_ttt(v->w_ttt, v->p_uttt->inner_tictactoes[TOPLEFT]);
|
|
||||||
}
|
|
||||||
wrefresh(stdscr);
|
|
||||||
do {
|
|
||||||
mvwprintw(stdscr, 1, 0, "le gagnant est : %c, apputez sur 'entree' pour quitter",
|
|
||||||
v->p_uttt->outer_tictactoe->winner);
|
|
||||||
ch = wgetch(stdscr);
|
|
||||||
} while (ch != '\n');
|
|
||||||
|
|
||||||
}
|
|
||||||
void free_view(p_view v){
|
void free_view(p_view v){
|
||||||
|
if(v->p_uttt->inception_level == 2){
|
||||||
delwin(v->w_uttt);
|
delwin(v->w_uttt);
|
||||||
v->w_uttt = NULL;
|
v->w_uttt = NULL;
|
||||||
|
}
|
||||||
delwin(v->w_ttt);
|
delwin(v->w_ttt);
|
||||||
v->w_ttt = NULL;
|
v->w_ttt = NULL;
|
||||||
v->w_uttt = NULL;
|
v->w_uttt = NULL;
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue