public void ReplaceRandomBranch(IRandom random, ISymbolicExpressionTree symbolicExpressionTree, int maxTreeLength, int maxTreeDepth) { var allowedSymbols = new List <ISymbol>(); ISymbolicExpressionTreeNode parent; int childIndex; int maxLength; int maxDepth; // repeat until a fitting parent and child are found (MAX_TRIES times) int tries = 0; do { #pragma warning disable 612, 618 parent = symbolicExpressionTree.Root.IterateNodesPrefix().Skip(1).Where(n => n.SubtreeCount > 0).SelectRandom(random); #pragma warning restore 612, 618 childIndex = random.Next(parent.SubtreeCount); var child = parent.GetSubtree(childIndex); maxLength = maxTreeLength - symbolicExpressionTree.Length + child.GetLength(); maxDepth = maxTreeDepth - symbolicExpressionTree.Root.GetBranchLevel(child); allowedSymbols.Clear(); foreach (var symbol in parent.Grammar.GetAllowedChildSymbols(parent.Symbol, childIndex)) { // check basic properties that the new symbol must have if ((symbol.Name != child.Symbol.Name || symbol.MinimumArity > 0) && symbol.InitialFrequency > 0 && parent.Grammar.GetMinimumExpressionDepth(symbol) <= maxDepth && parent.Grammar.GetMinimumExpressionLength(symbol) <= maxLength) { allowedSymbols.Add(symbol); } } tries++; } while (tries < MAX_TRIES && allowedSymbols.Count == 0); if (tries < MAX_TRIES) { var weights = allowedSymbols.Select(s => s.InitialFrequency).ToList(); #pragma warning disable 612, 618 var seedSymbol = allowedSymbols.SelectRandom(weights, random); #pragma warning restore 612, 618 // replace the old node with the new node var seedNode = seedSymbol.CreateTreeNode(); if (seedNode.HasLocalParameters) { seedNode.ResetLocalParameters(random); } CutPointSymbolParameter.ActualValue = (ISymbol)parent.Symbol.Clone(); RemovedBranchParameter.ActualValue = new SymbolicExpressionTree((ISymbolicExpressionTreeNode)parent.GetSubtree(childIndex).Clone()); parent.RemoveSubtree(childIndex); parent.InsertSubtree(childIndex, seedNode); ProbabilisticTreeCreator.PTC2(random, seedNode, maxLength, maxDepth); AddedBranchParameter.ActualValue = new SymbolicExpressionTree((ISymbolicExpressionTreeNode)parent.GetSubtree(childIndex).Clone()); } }
private static void DeletionByRandomRegeneration(IRandom random, ISymbolicExpressionTree symbolicExpressionTree, DefunTreeNode selectedDefunBranch) { // find first invocation and replace it with a randomly generated tree // can't find all invocations in one step because once we replaced a top level invocation // the invocations below it are removed already var invocationCutPoint = (from node in symbolicExpressionTree.IterateNodesPrefix() from subtree in node.Subtrees.OfType <InvokeFunctionTreeNode>() where subtree.Symbol.FunctionName == selectedDefunBranch.FunctionName select new CutPoint(node, subtree)).FirstOrDefault(); while (invocationCutPoint != null) { // deletion by random regeneration ISymbolicExpressionTreeNode replacementTree = null; var allowedSymbolsList = invocationCutPoint.Parent.Grammar.GetAllowedChildSymbols(invocationCutPoint.Parent.Symbol, invocationCutPoint.ChildIndex).ToList(); var weights = allowedSymbolsList.Select(s => s.InitialFrequency); #pragma warning disable 612, 618 var selectedSymbol = allowedSymbolsList.SelectRandom(weights, random); #pragma warning restore 612, 618 int minPossibleLength = invocationCutPoint.Parent.Grammar.GetMinimumExpressionLength(selectedSymbol); int maxLength = Math.Max(minPossibleLength, invocationCutPoint.Child.GetLength()); int minPossibleDepth = invocationCutPoint.Parent.Grammar.GetMinimumExpressionDepth(selectedSymbol); int maxDepth = Math.Max(minPossibleDepth, invocationCutPoint.Child.GetDepth()); replacementTree = selectedSymbol.CreateTreeNode(); if (replacementTree.HasLocalParameters) { replacementTree.ResetLocalParameters(random); } invocationCutPoint.Parent.RemoveSubtree(invocationCutPoint.ChildIndex); invocationCutPoint.Parent.InsertSubtree(invocationCutPoint.ChildIndex, replacementTree); ProbabilisticTreeCreator.PTC2(random, replacementTree, maxLength, maxDepth); invocationCutPoint = (from node in symbolicExpressionTree.IterateNodesPrefix() from subtree in node.Subtrees.OfType <InvokeFunctionTreeNode>() where subtree.Symbol.FunctionName == selectedDefunBranch.FunctionName select new CutPoint(node, subtree)).FirstOrDefault(); } }