//Reference:https://www.youtube.com/watch?v=UXW2yZndl7U private MCTSNode RunMCTS(int player, float modifier) { MCTSNode root = new MCTSNode(size); root.BoardState = mainBoard; root.parent = null; root.player = (activePlayer + 1) % 2; root.score = 0.0f; root.totalPlayouts = 0.0f; int totalIterations = 0; DateTime start = DateTime.Now; //while((DateTime.Now - start).Milliseconds < Time.maximumDeltaTime * 1000 * modifier) while (totalIterations < 100000) { MCTSNode current = root; //Selection while (current.children.Count != 0) { current = current.GetChildWithBestUCB1(); } //Simulation if (current.totalPlayouts == 0) { float score = Simulate(current.BoardState, activePlayer); //Back Propagate current.BackPropagate(score); } else { //Expansion current.Expand(); } totalIterations++; } //Find node with best score float bestScore = root.children[0].score / root.children[0].totalPlayouts; int selectedIndex = 0; for (int i = 1; i < root.children.Count; i++) { float score = root.children[i].score / root.children[i].totalPlayouts; if (bestScore < score) { bestScore = score; selectedIndex = i; } } return(root.children[selectedIndex]); }
/// <summary> /// Increment hits or misses according to the sign of the result /// Have the parent node do this as well /// </summary> /// <param name="result"></param> void BackPropagate(int result) { if (result > 0) { hits++; } if (result < 0) { misses++; } totalTrials++; if (parent != null) { // parent active player is opposite of this active player // so negate sign of result parent.BackPropagate(-result); } }