public void Action(position[,] state, ref List<stepmove> r) { // List<stepmove> r = new List<stepmove>(); for (int i = 0; i < 7; i++) { for (int j = 5; j >= 0; j--) { if (!state[i, j].occupied) { stepmove temp = new stepmove(); temp.pos = state[i, j].pos; temp.score = double.MinValue; r.Add(temp); break; } } } // return r; }
public bool winstate(position[,] state, int pcolor) { //Horizontal for (int i = 0; i < 7; i++) { for (int j = 0; j < 6 - 3; j++) { if (state[i,j].occupied&&(state[i, j].color == pcolor) && state[i,j+1].occupied&&(state[i, j+1].color == pcolor) && state[i,j+2].occupied&&(state[i, j+2].color == pcolor) && state[i,j+3].occupied&&(state[i, j+3].color == pcolor)) { start.X = i; start.Y = j; end.X = i; end.Y = j + 3; return true; } } } //Vertical for (int i = 0; i < 7 - 3; i++) { for (int j = 0; j < 6; j++) { if (state[i,j].occupied&&(state[i, j].color == pcolor) && state[i+1,j].occupied&&(state[i+1, j].color == pcolor) && state[i+2,j].occupied&&(state[i+2, j].color == pcolor) && state[i+3,j].occupied&&(state[i+3, j].color == pcolor)) { start.X = i; start.Y = j; end.X = i+3; end.Y = j; return true; } } } //Diagonal for (int i = 0; i < 7 - 3; i++) { for (int j = 0; j < 6 - 3; j++) { if (state[i, j].occupied && (state[i, j].color == pcolor) && state[i+1, j + 1].occupied && (state[i+1, j + 1].color == pcolor) && state[i+2, j + 2].occupied && (state[i+2, j + 2].color == pcolor) && state[i+3, j + 3].occupied && (state[i+3, j + 3].color == pcolor)) { start.X = i; start.Y = j; end.X = i+3; end.Y = j + 3; return true; } } } //Diagonal for (int i = 0; i < 7 - 3; i++) { for (int j = 3; j < 6; j++) { if (state[i, j].occupied && (state[i, j].color == pcolor) && state[i + 1, j - 1].occupied && (state[i + 1, j - 1].color == pcolor) && state[i + 2, j - 2].occupied && (state[i + 2, j - 2].color == pcolor) && state[i + 3, j - 3].occupied && (state[i + 3, j - 3].color == pcolor)) { start.X = i; start.Y = j; end.X = i+3; end.Y = j - 3; return true; } } } return false; }
public void result(position[,] state, stepmove a,int pcolor) { state[a.pos.X, a.pos.Y].pos = a.pos; state[a.pos.X, a.pos.Y].occupied = true; state[a.pos.X, a.pos.Y].color = pcolor; //return state; }
public double score(position[,] state,int pcolor) { double score = 0; double scoreTwo = 10; double scoreThree = 40; for (int i = 0; i < 7; i++) { for (int j = 0; j < 6; j++) { if (state[i, j].occupied == true) { //Vertical 2 if (j < 6 - 2) { if ((state[i, j + 1].color == pcolor) && (state[i, j + 2].color == pcolor)) score += scoreTwo; } //Vertical 2~ if (j >= 2) { if ((state[i, j - 1].color == pcolor) && (state[i, j - 2].color == pcolor)) score += scoreTwo; } //Horizontal 2 if (i < 7 - 2) { if ((state[i + 1, j].color == pcolor) && (state[i + 2, j].color == pcolor)) score += scoreTwo; //Diagonal 2 if (j < 6 - 2) { if ((state[i + 1, j + 1].color == pcolor) && (state[i + 2, j + 2].color == pcolor)) score += scoreTwo; } if (j >= 2) { if ((state[i + 1, j - 1].color == pcolor) && (state[i + 2, j - 2].color == pcolor)) score += scoreTwo; } } //Horizontal 2~ if (i >= 2) { if ((state[i - 1, j].color == pcolor) && (state[i - 2, j].color == pcolor)) score += scoreTwo; //Diagonal 2~ if (j < 6 - 2) { if ((state[i - 1, j + 1].color == pcolor) && (state[i - 2, j + 2].color == pcolor)) score += scoreTwo; } if (j >= 2) { if ((state[i - 1, j - 1].color == pcolor) && (state[i - 2, j - 2].color == pcolor)) score += scoreTwo; } } //Vertical 3 if (j < 6 - 3) { if ((state[i, j + 1].color == pcolor) && (state[i, j + 2].color == pcolor) && (state[i, j + 3].color == pcolor)) score += scoreThree; } //Vertical 3~ if (j >= 3) { if ((state[i, j - 1].color == pcolor) && (state[i, j - 2].color == pcolor) && (state[i, j - 3].color == pcolor)) score += scoreThree; } //Horizontal 3 if (i < 7 - 3) { if ((state[i + 1, j].color == pcolor) && (state[i + 2, j].color == pcolor) && (state[i + 3, j].color == pcolor)) score += scoreThree; //Diagonal 3 if (j < 6 - 3) { if ((state[i + 1, j + 1].color == pcolor) && (state[i + 2, j + 2].color == pcolor) && (state[i + 3, j + 3].color == pcolor)) score += scoreThree; } if (j >= 3) { if ((state[i + 1, j - 1].color == pcolor) && (state[i + 2, j - 2].color == pcolor) && (state[i + 3, j - 3].color == pcolor)) score += scoreThree; } } //Horizontal 3~ if (i >= 3) { if ((state[i - 1, j].color == pcolor) && (state[i - 2, j].color == pcolor) && (state[i - 3, j].color == pcolor)) score += scoreThree; //Diagonal 3~ if (j < 6 - 3) { if ((state[i - 1, j + 1].color == pcolor) && (state[i - 2, j + 2].color == pcolor) && (state[i - 3, j + 3].color == pcolor)) score += scoreThree; } if (j >= 3) { if ((state[i - 1, j - 1].color == pcolor) && (state[i - 2, j - 2].color == pcolor) && (state[i - 3, j - 3].color == pcolor)) score += scoreThree; } } } } } return score; }
public stepmove MinValue(position[,] s, stepmove next,double alpha, double beta, int depth) { position[,] state2 = new position[7, 6]; for (int i = 0; i < 7; i++) { for (int j = 0; j < 6; j++) { state2[i, j].pos.X = s[i, j].pos.X; state2[i, j].pos.Y = s[i, j].pos.Y; state2[i, j].color = s[i, j].color; state2[i, j].occupied = s[i, j].occupied; } } result(state2, next, 1); stepmove v; v.score = double.MaxValue; v.pos = next.pos; if (cutoff(state2, depth, 1)) { v.score = evaluation(state2, 1); return v; } List<stepmove> actionlist = new List<stepmove>(); Action(state2, ref actionlist); foreach (stepmove a in actionlist) { v.score = Math.Min(v.score, MaxValue(state2, a, alpha, beta, depth + 1).score); if (v.score <= alpha) return v; beta = Math.Min(beta, v.score); } return v; }
/* public bool isWin(int col, int row, position[,] state) { int connect = 1; //check right: for (int i = 1; i <= 3; i++) { if(col+i>6) break; else { if (state[col + i, row].occupied == false) break; else { if (state[col + i, row].color == player) connect++; else break; } } } if (connect == 4) return true; //check left: for (int i = 1; i <= 3; i++) { if (col - i < 0) break; else { if (state[col - i, row].occupied == true) { if (state[col - i, row].color == player) connect++; else break; } else break; } } if (connect == 4) return true; connect = 1; //check up: for (int i = 1; i <= 3; i++) { if (row - i < 0) break; else { if (state[col, row - i].occupied == true) { if (state[col, row - i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; //check down: for (int i = 1; i <= 3; i++) { if (row + i > 5) break; else { if (state[col, row + i].occupied == true) { if (state[col, row + i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; connect = 1; //check upright: for (int i = 1; i <= 3; i++) { if (col + i > 6 || row - i < 0) break; else { if (state[col + i, row - i].occupied == true) { if (state[col + i, row - i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; //check leftbottom: for (int i = 1; i <= 3; i++) { if (col - i < 0 || row + i > 5) break; else { if (state[col - i, row + i].occupied == true) { if (state[col - i, row + i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; connect = 1; //check upleft: for (int i = 1; i <= 3; i++) { if (col - i < 0 || row - i < 0) break; else { if (state[col - i, row - i].occupied == true) { if (state[col - i, row - i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; //check bottomright: for (int i = 1; i <= 3; i++) { if (col + i > 6 || row + i > 5) break; else { if (state[col + i, row + i].occupied == true) { if (state[col + i, row + i].color == player) connect++; else break; } else break; } } if (connect == 4) return true; return false; }*/ public bool isDraw(position[,] state) { int sum = 0; for (int i = 0; i < 7; i++) { if (state[i, 0].occupied == true) sum++; } if (sum == 7) return true; else return false; }
public int hminimax(int depth) { position[,] state = new position[7, 6]; for (int i = 0; i < 7; i++) { for (int j = 0; j < 6; j++) { state[i,j].pos.X=board[i, j].pos.X; state[i, j].pos.Y=board[i, j].pos.Y; state[i, j].color = board[i, j].color; state[i, j].occupied=board[i, j].occupied; } } //state[,] is a thinking board for minimax algorithm //v contains each action return move(position and score), r is for the final return value //1 is for human // double v = MaxValue(state, double.MinValue, double.MaxValue,depth); stepmove v,r; r.score = double.MaxValue; r.pos.X = -1; r.pos.Y = -1; List<stepmove> actionlist=new List<stepmove>(); Action(state, ref actionlist); foreach (stepmove a in actionlist) { v = MaxValue(state, a,double.MinValue, double.MaxValue, 1); if (v.score <= r.score) r = v; } return r.pos.X; }
public double evaluation(position[,] state, int pcolor) { if (winstate(state, pcolor)) { if (pcolor == 2)//computer return double.MinValue; else return double.MaxValue; } return score(state, 2) - score(state, 1); }
public bool cutoff(position[,] state, int depth,int pcolor) { if(winstate(state,pcolor)) return true; else if(depth>Maxlevel) return true; else return false; }