This commit is contained in:
Rob Pearce 2021-02-17 23:30:12 +11:00
parent 18ad1e286c
commit 1d1b1b932e
3 changed files with 98 additions and 14 deletions

4
.gitignore vendored Normal file
View File

@ -0,0 +1,4 @@
tak.dSYM/
upto
tak

View File

@ -1,2 +1,3 @@
tak: tak.c tak.h
tak: tak.c tak.h Makefile
rm -rf tak.dSYM
gcc -g -Wall -otak tak.c

105
tak.c
View File

@ -1,4 +1,7 @@
// TODO: why isnt this working: never move away from place that would give a win to other p
// TODO: trap ctrl-c
// TODO: trap ctrl-d
// TODO: taktak
#include <ctype.h>
#include <math.h>
#include <stdio.h>
@ -30,6 +33,7 @@
#define TRUE (-1)
#define FALSE (0)
#define ALL (-1)
#define ANY (-1)
#define BLACK "\e[0;30m"
#define BLUE "\e[0;36m"
@ -301,7 +305,9 @@ int rowhasmod(int sx, int sy, char mod, int who) {
for (x=0; x < w; x++) {
if (getmodxy(x,sy) == mod) {
count++;
if (who == ANY || getownernumxy(x,sy) == who) {
count++;
}
}
}
@ -316,7 +322,9 @@ int colhasmod(int sx, int sy, char mod, int who) {
for (y=0; y < h; y++) {
if (getmodxy(sx,y) == mod) {
count++;
if (who == ANY || getownernumxy(sx,y) == who) {
count++;
}
}
}
@ -433,14 +441,35 @@ void aiupdatetile(int x, int y) {
// If we DONT own this location, consider other stones in the same row/col
if (getownernumxy(x, y) != turn) {
n = countownedinrow(x,y,turn) - rowhasmod(x,y,turn,'|'); // dont include our walls since they don't count in roads
// walls actively count against value
// row
n = countownedinrow(x,y,turn);
snprintf(temp, 1024, "we own %d cells in this row", n);
modaivalue(x,y, n * 6, temp);
n = countownedincol(x,y,turn) - colhasmod(x,y,turn,'|'); // don't include our walls since they don't count in roads
snprintf(temp, 1024, "we own %d cells in this column", n);
n = rowhasmod(x,y,turn,'|') + rowhasmod(x,y,1-turn,'|');
snprintf(temp, 1024, "%d walls in this row", n);
modaivalue(x,y, -(n * 7), temp);
n = rowhasmod(x,y,1-turn,'^');
snprintf(temp, 1024, "%d opposing capstones in this row", n);
modaivalue(x,y, -(n * 10), temp);
// col
n = countownedincol(x,y,turn);
snprintf(temp, 1024, "we own %d cells in this col", n);
modaivalue(x,y, n * 6, temp);
n = colhasmod(x,y,'|',ANY);
snprintf(temp, 1024, "%d walls in this col", n);
modaivalue(x,y, -(n * 7), temp);
n = colhasmod(x,y,'^',1-turn);
snprintf(temp, 1024, "%d opposing capstones in this col", n);
modaivalue(x,y, -(n * 10), temp);
// opponent tiles in row, offset by our walls/caps
multi = 2;
a = rowhasmod(x,y,'^',turn);
@ -721,7 +750,10 @@ void checkfortak(int who) {
for (y=0; y < h; y++) {
for (x=0; x < w; x++) {
if (xywouldgivewinto(who, x, y)) {
tak[who] = TRUE;
if (canplacetile(who, x, y, ' ', NULL) ||
canmoveanyto(who, x, y, NULL, FALSE)) {
tak[who] = TRUE;
}
}
}
}
@ -772,8 +804,6 @@ int nextturn(void) {
// reset game log variables?
topofmove = ' ';
flattened = FALSE;
tak[0] = FALSE;
tak[1] = FALSE;
return 0;
}
@ -951,7 +981,6 @@ int movetile(int count,char xch,char ych, char dir, char *dropstr) {
return TRUE;
} else if ((mod == '|') && (remaining == 1) && (getmod(mp) == '^')) {
// single capstone moving onto a standing stone
// TODO: can yoi flatten yourbown standing stone?
if (pass == 1) {
if (debug) printf(" - %s%s%s capstone flattens %s%s%s standing stone at %c%c!\n",getpcol(turn),getpname(turn),reset,
getpcol(getowner(newbpos)),getpname(getowner(newbpos)), reset,
@ -1135,7 +1164,10 @@ int canmakedropstr(int who, int sx, int sy, int dx, int dy, char *str) { // retu
char *spos;
int smod;
char localstr[256];
int db = TRUE;
int db = FALSE;
int sizes[3][MAXSTACK];
int scount[3];
int tryidx,n,i;
spos=board[sy*w+sx];
smod = getmod(spos);
@ -1159,11 +1191,51 @@ int canmakedropstr(int who, int sx, int sy, int dx, int dy, char *str) { // retu
return FALSE;
}
// try each stack size
// try sizes that leave us in control of the initial tile
// first.
for (i=0; i<= 2; i++) { // 0 good, 1 bad, 2 good then bad
scount[i]=0;
}
if (db) {
printf("db: ** maxtry is.%d\n",maxtry);
}
for (trystacksize = 1; trystacksize <= maxtry; trystacksize++) {
p = spos + strlen(spos)-1;
if (ismod(*p)) p--;
p -= (trystacksize-1) ; // we're on the 1st tile that's moving
if (p>spos && (*(p-1) == getpchar(who))) {
// we own top of remaining stack
sizes[0][scount[0]++] = trystacksize;
} else {
// the other player owns it
sizes[1][scount[1]++] = trystacksize;
}
}
// combine lists, first good then bad
for (i=0;i<=1;i++) {
for (n=0;n<scount[i];n++) {
sizes[2][scount[2]++] = sizes[i][n];
}
}
if (db) {
printf("db: ** stack sizes to try: ");
for (tryidx = 0; tryidx < scount[2]; tryidx++) {
printf("%d(%c) ", sizes[2][tryidx],
tryidx >= scount[0] ? 'b' : 'g' );
}
printf("\n");
}
// try each stack size
for (tryidx = 0; tryidx < scount[2]; tryidx++) {
int x,y;
int stillgood = TRUE;
int xch,ych;
trystacksize = sizes[2][tryidx];
// pick up stack of tiles to move
p = spos + strlen(spos)-1;
if (ismod(*p)) p--;
@ -1461,6 +1533,7 @@ int parsecmd(char *cmd) {
if (!err) {
checkfortak(turn);
checkfortak(1-turn);
logmove(turn, cmd, topofmove);
}
@ -1558,9 +1631,15 @@ void showaivalues(int best) {
}
void showboard(void) {
int x,y;
int x,y,i;
char ch;
printf("\n%sRound %d - Turn %d (%s%s%s%s):\n", BOLD, curround, turnnumber, getpcol(turn), BOLD, getpname(turn), reset);
printf("\n%sRound %d - Turn %d (%s%s%s%s):", BOLD, curround, turnnumber, getpcol(turn), BOLD, getpname(turn), reset);
for (i=0; i<MAXPLAYERS; i++) {
if (tak[i]) {
printf(" %s---Tak:%s%s%s",getpcol(i), BOLD,getpname(i),reset);
}
}
printf("\n");
printf(FORMAT_ROWHEAD, ' ');
ch = 'a';
for (x=0; x < w; x++) {