private int minValue(StateNode currentNode, int depth, int alpha, int beta) { if (currentNode.isTerminalNode()) { currentNode.setAlpha(alpha); currentNode.setBeta(beta); StateNode.win_count++; return(currentNode.getValue()); } else { currentNode.setAlpha(alpha); currentNode.setBeta(beta); currentNode.setValue(1000); foreach (StateNode child in currentNode.Children) { currentNode.setValue(Math.Min(currentNode.getValue(), maxValue(child, depth++, currentNode.getAlpha(), currentNode.getBeta()))); currentNode.setBeta(Math.Min(currentNode.getBeta(), currentNode.getValue())); if (currentNode.getBeta() <= currentNode.getAlpha()) { return(currentNode.getValue()); } } return(currentNode.getValue()); } }
private void generateStates() { int MAX = 1; int MIN = 2; int TURNVAL = 0; bool MAXTURN = true; int CONNECTBY = 4; int M = 4; int N = 4; int MAXDEPTH = 9;//M * N; int DEPTH = 1; long count = 0; Queue <StateNode> currentLevel = new Queue <StateNode>(); Queue <StateNode> nextLevel = new Queue <StateNode>(); StateNode currentNode; currentLevel.Enqueue(root); //While the depth of the tree is less than or equal to 8 //and the number of nodes at the current level of the tree //is greater than 0 while (DEPTH <= MAXDEPTH && currentLevel.Count > 0) { if (MAXTURN) { TURNVAL = 1; } else { TURNVAL = 2; } //Switch turns in tree MAXTURN = !MAXTURN; //Probably not the best way to implement this, but //this loop will deplete the currentLevel, and then //repopulate it with the nodes from next level while (currentLevel.Count > 0) { //Find a node that has children and while currentLevel has children do { currentNode = currentLevel.Dequeue(); } while (currentNode.Children == null && currentLevel.Count > 0); for (int i = 0; i < N; i++) { bool STATEFILLED = false; int j = M - 1; if (currentNode.gridState[0, i] == 0) { while (j >= 0 && !STATEFILLED) { if (currentNode.gridState[j, i] == 0) { int[,] newState; StateNode newStateNode; newState = CopyArray(currentNode.gridState); newState[j, i] = TURNVAL; newStateNode = new StateNode(newState, currentNode); if (IsWinningTermState(newState, TURNVAL, CONNECTBY)) { newStateNode.Children = null; if (TURNVAL == MAX) { newStateNode.setValue(1 * DEPTH); } else { newStateNode.setValue(-1 * DEPTH); } } else if (IsNonWinningTermState(newState, TURNVAL)) { newStateNode.Children = null; newStateNode.setValue(0); } /*if (DEPTH >= (2 * CONNECTBY - 1)) * { * if (IsWinningTermState(newState, TURNVAL, CONNECTBY)) * { * newStateNode.Children = null; * if (TURNVAL == MAX) * newStateNode.setValue(1); * else * newStateNode.setValue(-1); * * } * else if( DEPTH == MAXDEPTH ) * { * newStateNode.Children = null; * newStateNode.setValue(0); * } * }*/ count++; currentNode.Children.AddLast(newStateNode); STATEFILLED = true; } j--; } } } foreach (StateNode n in currentNode.Children) { if (n.Children != null) { nextLevel.Enqueue(n); } } } while (nextLevel.Count > 0) { currentLevel.Enqueue(nextLevel.Dequeue()); } DEPTH++; } }