Forgot these files

This commit is contained in:
Olivier Teulière 2004-08-07 18:25:03 +00:00
parent b102aafbcd
commit f8074f5e02
2 changed files with 365 additions and 0 deletions

248
game/player.c Normal file
View file

@ -0,0 +1,248 @@
/* Eliot */
/* Copyright (C) 2004 Eliot */
/* Olivier Teuliere <ipkiss@via.ecp.fr> */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 2 of the License, or */
/* (at your option) any later version. */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program; if not, write to the Free Software */
/* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/* $Id: player.c,v 1.1 2004/08/07 18:25:03 ipkiss Exp $ */
#include <stdlib.h>
#include <string.h>
#include "dic.h"
#include "tiles.h"
#include "rack.h"
#include "pldrack.h"
#include "round.h"
#include "results.h"
#include "board.h"
#include "player.h"
#include "debug.h"
struct tplayer {
int human;
int score;
play_status status; /* Only used for duplicate mode currently */
/* History of the racks and rounds for the player */
int nracks;
Playedrack racks[PLAYEDRACK_MAX];
Round rounds[PLAYEDRACK_MAX];
int turns[PLAYEDRACK_MAX];
/* Results of a search with the current rack */
Results searchresults;
};
Player
Player_create(void)
{
int i;
Player p;
p = (Player) malloc(sizeof(struct tplayer));
if (p == NULL)
return NULL;
for (i = 0; i < PLAYEDRACK_MAX; i++)
{
p->racks[i] = Playedrack_create();
p->rounds[i] = Round_create();
}
p->searchresults = Results_create();
return p;
}
static void
Player_init(Player p, int human)
{
int i;
p->score = 0;
p->human = human;
p->status = TO_PLAY;
p->nracks = 0;
for (i = 0; i < PLAYEDRACK_MAX; i++)
{
Playedrack_init(p->racks[i]);
Round_init(p->rounds[i]);
}
Results_init(p->searchresults);
}
void
Player_inithuman(Player p)
{
Player_init(p, 1);
}
void
Player_initai(Player p)
{
Player_init(p, 0);
}
void
Player_destroy(Player p)
{
int i;
if (p)
{
for (i = 0; i < PLAYEDRACK_MAX; i++)
{
Playedrack_destroy(p->racks[i]);
Round_destroy(p->rounds[i]);
}
Results_destroy(p->searchresults);
free(p);
}
}
Playedrack
Player_getplayedrack(Player p)
{
return p->racks[p->nracks];
}
Playedrack
Player_getlastrack(Player p)
{
return p->racks[p->nracks - 1];
}
Round
Player_getlastround(Player p)
{
return p->rounds[p->nracks - 1];
}
int
Player_getpoints(Player p)
{
return p->score;
}
void
Player_addpoints(Player p, int s)
{
p->score += s;
}
void
Player_setstatus(Player p, play_status stat)
{
p->status = stat;
}
play_status
Player_getstatus(Player p)
{
return p->status;
}
/*
* This function increments the number of racks, and fills the new rack
* with the unplayed tiles from the previous one.
* 03 sept 2000 : We have to sort the tiles according to the new rules
*/
void
Player_endturn(Player p, Round round, int turn)
{
tile_t i;
Rack rack;
p->turns[p->nracks] = turn;
Round_copy(p->rounds[p->nracks], round);
/* Increment the number of racks
* We are now going to deal with p->racks[p->nracks - 1] and
* p->racks[p->nracks] */
p->nracks++;
rack = Rack_create();
Playedrack_getrack(p->racks[p->nracks - 1], rack);
/* We remove the played tiles from the rack */
for (i = 0; i < Round_wordlen(round); i++)
{
if (Round_playedfromrack(round, i))
{
if (Round_joker(round,i))
Rack_remove(rack, (tile_t)JOKER_TILE);
else
Rack_remove(rack, Round_gettile(round, i));
}
}
Playedrack_init(p->racks[p->nracks]);
Playedrack_setold(p->racks[p->nracks], rack);
Rack_destroy(rack);
}
int
Player_ai(Player p)
{
return ! p->human;
}
int
Player_ai_search(Player p, Dictionary dic, Board board, int turn)
{
Rack rack;
if (dic == NULL)
return 1;
Results_init(p->searchresults);
rack = Rack_create();
Playedrack_getrack(p->racks[p->nracks], rack);
if (turn == 0)
Board_search_first(dic, board, rack, p->searchresults);
else
Board_search(dic, board, rack, p->searchresults);
Rack_destroy(rack);
return 0;
}
Round
Player_ai_bestround(Player p)
{
return Results_get(p->searchresults, 0);
}
Results
Player_ai_getresults(Player p)
{
return p->searchresults;
}

117
game/player.h Normal file
View file

@ -0,0 +1,117 @@
/* Eliot */
/* Copyright (C) 2004 Eliot */
/* Olivier Teuliere <ipkiss@via.ecp.fr> */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 2 of the License, or */
/* (at your option) any later version. */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program; if not, write to the Free Software */
/* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/* $Id: player.h,v 1.1 2004/08/07 18:25:03 ipkiss Exp $ */
#ifndef _PLAYER_H_
#define _PLAYER_H_
#if defined(__cplusplus)
extern "C" {
#endif
/* Number of played words.
* There are only 102 tiles, so we should be safe even if only one tile is
* played at each turn... */
#define PLAYEDRACK_MAX 102
/*************************
* A player can be a human player, or a computer player (AI)
*************************/
typedef struct tplayer *Player;
/*************************
* Player general routines
*************************/
Player Player_create (void);
void Player_inithuman (Player);
void Player_initai (Player);
void Player_destroy (Player);
/**************************
* General getters
**************************/
Playedrack Player_getplayedrack (Player);
Playedrack Player_getlastrack (Player);
Round Player_getlastround (Player);
/**************************
*
**************************/
void Player_endturn (Player,Round,int);
/**************************
* Add (or remove, if the given value is negative) points
* to the player's score.
**************************/
void Player_addpoints (Player,int);
int Player_getpoints (Player);
/**************************
*
**************************/
typedef enum {PLAYED, TO_PLAY} play_status;
void Player_setstatus (Player,play_status);
play_status Player_getstatus (Player);
/**************************
* AI (Artificial Intelligence) handling
* The int argument of Player_ai_search() is the 'turn' number
* (starting from 0)
* Note: we could implement various strategies:
* - best: play the word with the best score (current implementation)
* - second: play the word with the second best score (strictly lower than
* the best one)
* - random: randomly choose one of the possible words
* - handicap(p): in the array of the n possible words (sorted by
* decreasing scores), play the word number i, where i/n is nearest
* from a predefined percentage p.
* So 'handicap(0)' should be equivalent to 'best'.
* This strategy makes an interesting opponent, because you can adapt
* it to your level, with a careful choice of the p value.
*
* In fact, instead of working on the score of the words, these strategies
* could work on any other value. In particular, some heuristics could
* modulate the score with a value indicating the openings offered by the
* word (if a word makes accessible a "word counts triple" square, it is less
* interesting than another word with the same score or even with a slightly
* lower score, but which does not offer such a square).
*
* More evolved heuristics could even take into account the remaining letters
* in the bag to guess the 'statistical rack' of the opponent, and play a
* word both maximizing the score and minimizing the opponent's score...
* Hmmm... i don't think this one will be implemented in a near future :)
**************************/
int Player_ai (Player);
int Player_ai_search (Player,Dictionary,Board,int);
Round Player_ai_bestround (Player); // XXX: useful?
Results Player_ai_getresults (Player);
#if defined(__cplusplus)
}
#endif
#endif