// -------------------------------------------------------------------------------------------- static void ProcessNode(PositionEvalCache cache, MCTSNode node, float weightEmpirical, bool saveToCache, bool rewriteNodeInTree) { Span <MCTSNodeStructChild> children = node.Ref.Children; // TODO: optimize this away if saveToCache is false ushort[] probabilities = new ushort[node.NumPolicyMoves]; ushort[] indices = new ushort[node.NumPolicyMoves]; // Compute empirical visit distribution float[] nodeFractions = new float[node.NumPolicyMoves]; for (int i = 0; i < node.NumChildrenExpanded; i++) { nodeFractions[i] = (float)node.ChildAtIndex(i).N / (float)node.N; } // Determine P of first unexpanded node // We can't allow any child to have a new P less than this // since we need to keep them in order by P and the resorting logic below // can only operate over expanded nodes float minP = 0; if (node.NumChildrenExpanded < node.NumPolicyMoves) { minP = node.ChildAtIndexInfo(node.NumChildrenExpanded).p; } // Add each move to the policy vector with blend of prior and empirical values for (int i = 0; i < node.NumChildrenExpanded; i++) { (MCTSNode node, EncodedMove move, FP16 p)info = node.ChildAtIndexInfo(i); indices[i] = (ushort)info.move.IndexNeuralNet; float newValue = (1.0f - weightEmpirical) * info.p + weightEmpirical * nodeFractions[i]; if (newValue < minP) { newValue = minP; } probabilities[i] = CompressedPolicyVector.EncodedProbability(newValue); if (rewriteNodeInTree && weightEmpirical != 0) { MCTSNodeStructChild thisChild = children[i]; if (thisChild.IsExpanded) { ref MCTSNodeStruct childNodeRef = ref thisChild.ChildRef; thisChild.ChildRef.P = (FP16)newValue; } else { node.Ref.ChildAtIndex(i).SetUnexpandedPolicyValues(thisChild.Move, (FP16)newValue); } } }
static LC0VerboseMoveStat BuildStatNotExpanded(MCTSNode node, int childIndex) { MCTSNodeStructChild child = node.ChildAtIndexRef(childIndex); LC0VerboseMoveStat stat = new LC0VerboseMoveStat(null, null); stat.MoveString = child.Move.ToString(); stat.MoveCode = child.Move.IndexNeuralNet; stat.P = child.P * 100.0f; stat.U = node.ChildU(childIndex); return(stat); }
internal static void Repack(MCTSNode node, ref CompressedPolicyVector policy) { Span <ushort> indicies = stackalloc ushort[node.NumPolicyMoves]; Span <ushort> probabilities = stackalloc ushort[node.NumPolicyMoves]; for (int i = 0; i < node.NumPolicyMoves; i++) { ref MCTSNodeStructChild childRef = ref node.ChildAtIndexRef(i); indicies[i] = (ushort)childRef.Move.IndexNeuralNet; probabilities[i] = CompressedPolicyVector.EncodedProbability(childRef.P); }