public void MutateAddNode(Population pop) { var choice = Config.globalRandom.Next(0, Connections.Count); var existingConnection = Connections[choice]; if (existingConnection.InputNode == 9999) { return; } //check if existingConnection has been split before int newNodeID; if (pop.AddedConnections.Keys.Contains(existingConnection.GetID())) { newNodeID = pop.AddedConnections[existingConnection.GetID()]; } else { newNodeID = Config.newNodeCounter++; pop.AddedConnections[existingConnection.GetID()] = newNodeID; } var choices = new List <string>() { "sin", "rescale", "square" }; var pick = choices[Config.globalRandom.Next(0, choices.Count)]; var newNode = new NodeGene(newNodeID, "hidden", pick); //exit if this innovation has been created before if (Nodes.Contains(newNode)) { return; } var existingBiasConnection = Connections.Single(x => x.InputNode == 9999 & x.OutputNode == existingConnection.OutputNode); //new connection in has weight 1 var newConnectionIn = new ConnectionGene(existingConnection.InputNode, newNode._id, 1.0); //new connection out has weight equal to old connection var newConnectionOut = new ConnectionGene(newNode._id, existingConnection.OutputNode, existingConnection.Weight); //should improve this, using 9999 to signify bias is kinda ugly var newConnectionBias = new ConnectionGene(9999, newNode._id, 1.0); Nodes.Add(newNode); Connections.Add(newConnectionIn); Connections.Add(newConnectionOut); Connections.Add(newConnectionBias); Connections.Remove(existingConnection); CalculateInputs(); }
//copy constructor public NodeGene(NodeGene parent) { _id = parent._id; _type = parent._type; _inputs = new List <int>(); foreach (int i in parent._inputs) { _inputs.Add(i); } Activation = parent.Activation; }