Example #1
0
        private void AddNodeMutation()
        {
            if (Connections.Count == 0)
            {
                return;
            }
            ConnectionGene connection;
            int            attempts = 0;

            do
            {
                attempts++;
                if (attempts > 100)
                {
                    return;
                }
                connection = Connections[RandomInt(Connections.Count)];
            }while (connection.Expressed == false);

            connection.Expressed = false;
            NodeGene newNode = new NodeGene(NodeGene.NodeType.Hidden,
                                            GetMaxNodeIndex() + 1,
                                            new Position(
                                                (connection.InNode.DrawPosition.x + connection.OutNode.DrawPosition.x) / 2,
                                                (connection.InNode.DrawPosition.y + connection.OutNode.DrawPosition.y) / 2));

            if (!ValidatNodePair((connection.InNode, newNode)))
            {
                throw new ArgumentException(string.Format(
                                                "AddNodeMutation tried to add bad node pair {0}, {1}", connection.InNode.Index, newNode.Index));
            }
            if (!ValidatNodePair((newNode, connection.OutNode)))
            {
                throw new ArgumentException(string.Format(
                                                "AddNodeMutation tried to add bad node pair {0}, {1}", newNode.Index, connection.OutNode.Index));
            }

            ConnectionGene newConnection1 = new ConnectionGene(connection.InNode, newNode);
            ConnectionGene newConnection2 = new ConnectionGene(newNode, connection.OutNode);

            newConnection1.Weight = 1;
            newConnection2.Weight = connection.Weight;

            AddConnection(newConnection1);
            AddConnection(newConnection2);
            Nodes.Add(newNode);
        }
Example #2
0
        /// <summary>
        /// Gets a (new) NodeGene for this Generation from existing ConnectionGene
        /// </summary>
        /// <param name="connectionOld">Connection to create Node for. Passed by reference in order to disable it</param>
        /// <param name="connectionNew1">OUT: New Connection from old In-Node to new Node</param>
        /// <param name="connectionNew2">OUT: New Connection from new Node to old Out-Node</param>
        /// <returns>Created NodeGene</returns>
        internal static NodeGene GetNode(ref ConnectionGene connectionOld, out ConnectionGene connectionNew1, out ConnectionGene connectionNew2)
        {
            connectionOld.Disable();
            NodeGene newNode;

            if (generationNodes.ContainsKey(connectionOld.Innovation)) // Exists
            {
                newNode = generationNodes[connectionOld.Innovation];
            }
            else
            {
                newNode = new NodeGene(NodeType.HIDDEN);                // New Node (Can only be a hidden node, as it is between other nodes)
            }
            connectionNew1 = GetConnection(connectionOld.In, newNode);  // Get/Create Connection from Old In to Gene
            connectionNew2 = GetConnection(newNode, connectionOld.Out); // Get/Create Connection from Gene to Old Out
            return(newNode);
        }
Example #3
0
        /// <summary>
        ///  Creates a new ConnectionGene to track and adds it to the tracker.
        /// </summary>
        /// <param name="from">The NodeGene to connect from.</param>
        /// <param name="to">The NodeGene to connect to.</param>
        /// <returns>The created ConnectionGene.</returns>
        public ConnectionGene CreateConnection(NodeGene from, NodeGene to)
        {
            ConnectionGene connectionGene = new ConnectionGene(from, to, 0);    //Temp innovation number.

            if (all_connections.ContainsKey(connectionGene))
            {
                connectionGene.InnovationNumber = all_connections[connectionGene].InnovationNumber;
            }
            else
            {
                connectionGene.InnovationNumber = all_connections.Count + 1;

                all_connections.Add(connectionGene, connectionGene);
            }

            return(connectionGene);
        }
Example #4
0
    public void RemoveLink(float mutationRate)
    {
        if (Random.Range(0f, 1f) > mutationRate)
        {
            return;
        }

        int            con_num    = Random.Range(0, connections.Count);
        ConnectionGene connection = connections[con_num];

        int from = connection.from;
        int to   = connection.to;


        connections.RemoveAt(con_num);

        if (from == to)
        {
            return;
        }

        int fromIndex = 0;
        int toIndex   = 0;

        for (int i = 0; i < connections.Count; i++)
        {
            if (connections[i].to == to || connections[i].from == to)
            {
                toIndex++;
            }

            if (connections[i].to == from || connections[i].from == from)
            {
                fromIndex++;
            }
        }

        if (fromIndex == 0 && perceptrons[GetElementPos(from)].type == NodeType.Hidden)
        {
            perceptrons.RemoveAt(GetElementPos(from));
        }
        if (toIndex == 0 && perceptrons[GetElementPos(to)].type == NodeType.Hidden)
        {
            perceptrons.RemoveAt(GetElementPos(to));
        }
    }
Example #5
0
 /// <summary>
 /// Adds a ConnectionGene to this Genome. Overwrites if ConnectionGene with Innovation-Number exists
 /// </summary>
 /// <param name="gene">ConnectionGene to add</param>
 private void AddConnection(ConnectionGene gene)
 {
     if (!gene.IsValid)
     {
         throw new ArgumentException("Connection is not Valid", "gene");
     }
     if (Connections.ContainsKey(gene.Innovation))
     {
         Connections[gene.Innovation] = gene;
     }
     else
     {
         Connections.Add(gene.Innovation, gene);
     }
     AddNode(gene.In);
     AddNode(gene.Out);
 }
Example #6
0
    public void AddNodeMutation()
    {
        if (neat.maxNeurones <= nodes.Count)
        {
            return;
        }

        ConnectionGene connectionSplit = connections[Random.Range(0, connections.Count)];//choose random connection to split

        connectionSplit.Disable();



        NodeGene nodeIn = connectionSplit.GetInNode();

        NodeGene nodeOut = connectionSplit.GetOutNode();

        //Debug.Log("nin" + nodeIn.GetLayer());
        //Debug.Log("nout"+ nodeOut.GetLayer());
        int newLayer;

        if (nodeOut.GetLayer() - nodeIn.GetLayer() == 1)
        {
            //Debug.Log(nodeIn.GetLayer());
            //Debug.Log(nodeOut.GetLayer());
            newLayer = nodeOut.GetLayer();
            AddLayer(nodeOut.GetLayer());
            //Debug.Log("new layer" + nodeOut.GetLayer());
            //newLayer = nodeOut.GetLayer();
        }
        else
        {
            newLayer = Random.Range(nodeIn.GetLayer() + 1, nodeOut.GetLayer() - 1);
        }


        NodeGene node = new NodeGene(NodeGene.NODETYPE.HIDDEN, track.NewId(), newLayer, Random.Range(-1.0f, 1.0f), neat.internalActiationFunction);

        nodes.Add(node);

        ConnectionGene connectionIn  = new ConnectionGene(connectionSplit.GetInNode().Copy(), node, 1.0f, true, track.Innovate());
        ConnectionGene connectionOut = new ConnectionGene(node, connectionSplit.GetOutNode().Copy(), connectionSplit.GetWeight(), true, track.Innovate());

        connections.Add(connectionIn);
        connections.Add(connectionOut);
    }
Example #7
0
 void mutationAddConnection(float mutationChance, InnovationAssigner cIA)
 {
     foreach (var n in neuronGenes)
     {
         if (!n.Value.isInput)
         {
             if (Random.Range(0f, 1f) <= mutationChance)
             {
                 int[]          candidates    = getInputCandidates(n.Value.layer);
                 int            chosen        = candidates[Random.Range(0, candidates.Length)];
                 float          weight        = Random.Range(-1f, 1f);
                 ConnectionGene newConnection = new ConnectionGene(cIA.getInnovation(), chosen, n.Value.innovation, weight);
                 connectionGenes.Add(newConnection.innovation, newConnection);
                 //Debug.Log("New connection from " + newConnection.fromNeuronInnovation + " to " + newConnection.toNeuronInnovation);
             }
         }
     }
 }
Example #8
0
        public Genome copy()
        {
            Genome copy = new Genome();

            copy.neuronGenes = new Dictionary <int, NeuronGene>();
            foreach (var n in neuronGenes)
            {
                NeuronGene ng = n.Value.copy();
                copy.neuronGenes.Add(ng.innovation, ng);
            }
            copy.connectionGenes = new Dictionary <int, ConnectionGene>();
            foreach (var c in connectionGenes)
            {
                ConnectionGene cg = c.Value.copy();
                copy.connectionGenes.Add(cg.innovation, cg);
            }
            return(copy);
        }
Example #9
0
        public void TestReEnableCreatesCycle()
        {
            // Test that a gene already in the genome can be tested fro recurrence
            NeatBrainGenotype test = new NeatBrainGenotype();

            test.AddNamedNode("input1", NodeType.INPUT, ActivationFunctionType.RELU);
            test.AddNamedNode("hidden1", NodeType.HIDDEN, ActivationFunctionType.RELU);
            test.AddNamedNode("output1", NodeType.OUTPUT, ActivationFunctionType.RELU);

            test.ConnectionGenes.Add(new ConnectionGene(1, 0, 1, 1));
            var recurrentGene = new ConnectionGene(2, 1, 1, 1, false, true);

            test.ConnectionGenes.Add(recurrentGene);
            test.ConnectionGenes.Add(new ConnectionGene(3, 1, 2, 1));

            // This new gene should not create a cycle
            Assert.IsTrue(test.CreatesCycle(recurrentGene));
        }
Example #10
0
    public void AddNoteMutation_Test()
    {
        //Test list size before modifying
        Assert.AreEqual(parent1Genome.Connections.Values.Count, 6);
        Assert.AreEqual(parent1Genome.Nodes.Values.Count, 5);

        ConnectionGene splittedConnection = parent1Genome.Connections[3];
        object[] result = parent1Genome.AddNodeMutation(splittedConnection, 7, 11, 12);

        //Test if a node and connections were added
        Assert.AreEqual(parent1Genome.Connections.Values.Count, 8);
        Assert.AreEqual(parent1Genome.Nodes.Values.Count, 6);

        //Test the amount of results
        Assert.AreEqual(result.Length, 4);

        //Compare the disabled connection with the connection from the result
        Assert.AreEqual(splittedConnection, (ConnectionGene)result[0]);
        Assert.AreEqual(false, splittedConnection.Expressed);

        //Check ne newly created node
        NodeGene newNode = (NodeGene)result[1];
        Assert.AreEqual(NodeGeneType.HIDDEN, newNode.Type);
        Assert.AreEqual(newNode, parent1Genome.Nodes[newNode.ID]);
        Assert.AreEqual(7, newNode.ID);

        //Check the new connections
        ConnectionGene inToNew = (ConnectionGene)result[2];
        ConnectionGene newToOut = (ConnectionGene)result[3];

        //Check the in to new connection
        Assert.AreEqual(splittedConnection.InNode, inToNew.InNode);
        Assert.AreEqual(1.0, inToNew.Weight);
        Assert.AreEqual(newNode.ID, inToNew.OutNode);
        Assert.AreEqual(11, inToNew.InnovationNumber);
        Assert.AreEqual(inToNew, parent1Genome.Connections[inToNew.InnovationNumber]);

        //Check the new to out connection
        Assert.AreEqual(newNode.ID, newToOut.InNode);
        Assert.AreEqual(splittedConnection.Weight, newToOut.Weight);
        Assert.AreEqual(splittedConnection.OutNode, newToOut.OutNode);
        Assert.AreEqual(12, newToOut.InnovationNumber);
        Assert.AreEqual(newToOut, parent1Genome.Connections[newToOut.InnovationNumber]);
    }
Example #11
0
        ///<inheritdoc/>
        public void MutateNode()
        {
            ConnectionGene connection = Connections.RandomElement();

            if (connection == null)
            {
                return;
            }

            NodeGene from = connection.In;
            NodeGene to   = connection.Out;

            int replaceIndex = Neat.GetReplaceIndex(from, to);

            NodeGene middle;

            if (replaceIndex == 0)
            {
                ActivationEnumeration a = ActivationEnumeration.Random();
                middle                = Neat.CreateNode();
                middle.X              = (from.X + to.X) / 2;
                middle.Y              = ((from.Y + to.Y) / 2) + (ThreadSafeRandom.NormalRand(0, 0.02f) / 2);
                middle.Activation     = a.Activation;
                middle.ActivationName = a.Name;
                Neat.SetReplaceIndex(from, to, middle.InnovationNumber);
            }
            else
            {
                middle = Neat.GetNode(replaceIndex);
            }

            ConnectionGene connection1 = Neat.GetConnection(from, middle);
            ConnectionGene connection2 = Neat.GetConnection(middle, to);

            connection1.Weight  = 1;
            connection2.Weight  = connection.Weight;
            connection2.Enabled = connection.Enabled;

            connection.Enabled = false;
            Connections.Add(connection1);
            Connections.Add(connection2);

            Nodes.Add(middle);
        }
Example #12
0
        public void InsertConnectionGene(ConnectionGene gene)
        {
            if (gene == null)
            {
                throw new ArgumentNullException(nameof(gene));
            }

            int innovation = gene.Innovation;
            int i;

            for (i = 0; i < this.connectionGenes.Count; ++i)
            {
                if (this.connectionGenes[i].Innovation >= innovation)
                {
                    break;
                }
            }
            this.connectionGenes.Insert(i, gene);
        }
Example #13
0
        public static void MutateAddConnection(this Genome genome, bool forceBias = false)
        {
            NodeGene firstNode;

            if (forceBias)
            {
                firstNode = genome.NodeGenes.Values.Where(g => g.Type == NodeGeneType.Input).Last();
            }
            else
            {
                firstNode = genome.NodeGenes.Values.GetRandomElement();
            }

            var secondNode = genome.NodeGenes.Values.GetRandomElement();
            // TODO: Fix this hack that prevent possible endless loop
            int limiter = 0;

            while (firstNode.Id == secondNode.Id ||
                   genome.ConnectionGenes.GetConnection(firstNode, secondNode) != null ||
                   firstNode.Type == NodeGeneType.Input && secondNode.Type == NodeGeneType.Input ||
                   firstNode.Type == NodeGeneType.Output && secondNode.Type == NodeGeneType.Output)
            {
                secondNode = genome.NodeGenes.Values.GetRandomElement();
                if (limiter > 100)
                {
                    return;
                }
                limiter++;
            }

            if (firstNode.Type == NodeGeneType.Output && secondNode.Type == NodeGeneType.Hidden ||
                firstNode.Type == NodeGeneType.Hidden && secondNode.Type == NodeGeneType.Input ||
                firstNode.Type == NodeGeneType.Output && secondNode.Type == NodeGeneType.Input)
            {
                var tmp = secondNode;
                secondNode = firstNode;
                firstNode  = tmp;
            }

            var newConnection = new ConnectionGene(firstNode.Id, secondNode.Id);

            genome.AddConnectionGene(newConnection);
        }
Example #14
0
        private void UpdateGeneWeight(ConnectionGene geneToChange, double gaussPoint, double coldGaussPoint, double randomWeight)
        {
            double randchoice = this.random.NextDouble();

            if (randchoice > gaussPoint)
            {
                geneToChange.Weight += (float)randomWeight;
            }
            else if (randchoice > coldGaussPoint)
            {
                geneToChange.Weight = (float)randomWeight;
            }


            if (this.ParentSimulation.Parameters.AreConnectionWeightsCapped)
            {
                geneToChange.Weight.Clamp(-this.ParentSimulation.Parameters.MaxWeight, this.ParentSimulation.Parameters.MaxWeight);
            }
        }
Example #15
0
        public void ToggleEnabledMutation()
        {
            // Handle special case when one of the genomes is completely empty
            if (this.connectionGenes.Count == 0)
            {
                return;
            }

            int            counter      = 0;
            bool           isOkToToggle = false;
            ConnectionGene gene         = null;

            while (counter++ < maxTries && !isOkToToggle)
            {
                gene = this.connectionGenes[this.random.Next(connectionGenes.Count)];
                // If gene is enabled, we have first check if that's safe to disable it:
                // i.e. if there exists another gene connecting to the In-Node.
                if (gene.IsEnabled)
                {
                    foreach (ConnectionGene checkGene in this.connectionGenes)
                    {
                        if (checkGene.InNodeGene == gene.InNodeGene && checkGene.IsEnabled && checkGene.Innovation != gene.Innovation)
                        {
                            isOkToToggle = true;
                            break;
                        }
                    }
                }
                else
                {
                    // It's always safe to reenable the gene
                    isOkToToggle = true;
                }
            }

            // Toggle gene's enabled state if it's safe to do so
            if (isOkToToggle)
            {
                gene.IsEnabled        = !gene.IsEnabled;
                this.phenotypeChanged = true;
            }
        }
Example #16
0
    public float GetActivation(float[] inputs)
    {
        if (type == TYPE.SENSOR)
        {
            return(inputs[id - 1]);
        }

        else
        {
            float summedActivation = 0;
            foreach (NodeGene node in directInNodes.Keys)
            {
                ConnectionGene connectionIn = directInNodes[node];

                summedActivation += (connectionIn.getExpressed())? node.GetActivation(inputs) * connectionIn.getWeight() : 0;
            }

            return(History.Sigmoid(summedActivation));
        }
    }
Example #17
0
        private void AddConnectionGeneToChild(Genome child, ConnectionGene newGene)
        {
            // Check if there aren't any conflicts with an existing connection
            bool skip = false;

            foreach (ConnectionGene g in child.ConnectionGenes)
            {
                if ((g.InNodeGene.ID == newGene.InNodeGene.ID && g.OutNodeGene.ID == newGene.OutNodeGene.ID && g.IsRecurrent == newGene.IsRecurrent) ||
                    (g.InNodeGene.ID == newGene.OutNodeGene.ID && g.OutNodeGene.ID == newGene.InNodeGene.ID && !g.IsRecurrent && !newGene.IsRecurrent))
                {
                    skip = true;
                    break;
                }
            }

            if (!skip)
            {
                child.AddConnectionGene(newGene);
            }
        }
Example #18
0
        public void Equals_ReturnsTrue()
        {
            if (!Genome.IsInitialized())
            {
                Genome.Init();
            }


            NodeGene from = new NodeGene(1, Node.INPUT_X, Neural_Network.Node.Sigmoid);

            NodeGene to = new NodeGene(2, Node.INPUT_X, Neural_Network.Node.Sigmoid);


            ConnectionGene connectionGene_1 = new ConnectionGene(from, to, 1);

            ConnectionGene connectionGene_2 = new ConnectionGene(from, to, 1);


            Assert.IsTrue(connectionGene_1 == connectionGene_2);
        }
Example #19
0
        /// <summary>
        /// Adds Node for Connection (Structural Mutation)
        /// </summary>
        /// <param name="connectionInnovation">Connection to add Node for</param>
        internal void MutateAddNode(ConnectionGene conn)
        {
            if (!conn.IsValid)
            {
                throw new ArgumentException("Connection is not Valid", "conn");
            }
            if (!conn.Expressed)
            {
                return; // Connection is not active
            }
            ConnectionGene conn1, conn2;
            NodeGene       newNode = MutationFactory.GetNode(ref conn, out conn1, out conn2);

            // Overwrite old Connection (now disabled)
            Connections[conn.Innovation] = conn;
            // Add new Objects
            AddNode(newNode);
            AddConnection(conn1);
            AddConnection(conn2);
        }
Example #20
0
        /// <summary>
        /// Returns True if the addition/re-enabling of the given gene will create a cycle in the genome's graph
        /// </summary>
        /// <param name="newGene">The gene to query.</param>
        /// <returns></returns>
        public bool CreatesCycle(ConnectionGene newGene)
        {
            if (newGene.Source == newGene.To)
            {
                return(true);
            }

            var visited              = new HashSet <int>();
            var toExpand             = new Stack <int>();
            var connectionDictionary = CreateConnectionDictionary();
            var targetNode           = newGene.To;

            //DFS to find if this creates a loop
            toExpand.Push(newGene.Source);

            while (toExpand.Count > 0)
            {
                var currentNode = toExpand.Pop();
                visited.Add(currentNode);

                if (connectionDictionary.ContainsKey(currentNode))
                {
                    foreach (int source in connectionDictionary[currentNode])
                    {
                        if (source == targetNode)
                        {
                            return(true);
                        }

                        if (visited.Contains(source))
                        {
                            // Avoid already visited nodes
                            continue;
                        }

                        toExpand.Push(source);
                    }
                }
            }
            return(false);
        }
Example #21
0
    //Split a random connection into 2 connections
    public void AddNodeMutation()
    {
        List <ConnectionGene> values = Enumerable.ToList(connections.Values);
        ConnectionGene        con    = values[Random.Range(0, values.Count)];

        NodeGene inNode  = nodes[con.inNode];
        NodeGene outNode = nodes[con.outNode];



        con.expressed = false;

        NodeGene newNode = new NodeGene(NodeGene.Type.Hidden, Counter.NextNode());

        ConnectionGene inToNew  = new ConnectionGene(inNode.id, newNode.id, 1f, true, Counter.NextConnection());
        ConnectionGene newToOut = new ConnectionGene(newNode.id, outNode.id, con.weight, true, Counter.NextConnection());

        nodes.Add(newNode.id, newNode);
        connections.Add(inToNew.innovation, inToNew);
        connections.Add(newToOut.innovation, newToOut);
    }
Example #22
0
 public Connection(ConnectionGene con, NodeGene.Type inType, NodeGene.Type outType)
 {
     inNode    = con.inNode;
     outNode   = con.outNode;
     value     = 0f;
     ready     = false;
     weight    = con.weight;
     recurrent = false;
     if (inType == NodeGene.Type.Output && (outType == NodeGene.Type.Input || outType == NodeGene.Type.Hidden))
     {
         recurrent = true;
     }
     else if (inType == NodeGene.Type.Hidden && outType == NodeGene.Type.Input)
     {
         recurrent = true;
     }
     else if (inType == outType)
     {
         recurrent = true;
     }
 }
Example #23
0
        /// <summary>
        /// Creates a node gene with the intention of splitting the given connection gene. Gives it a random known activation function.
        /// </summary>
        /// <remarks>
        /// If the node gene pattern does not yet exist, it will be created. Its innovation number will be the replacing number in the given connection gene's pattern. The X will be the
        /// average of the Xs in the given connection gene pattern's From/To nodes.
        /// </remarks>
        /// <param name="connectionGene">The connection gene with the intention of splitting.</param>
        /// <returns>The created node gene.</returns>
        /// <exception cref="ArgumentNullException">When the connection gene is null.</exception>
        public NodeGene Create_NodeGene(ConnectionGene connectionGene)
        {
            Helpers.ThrowOnNull(connectionGene, "connectionGene");


            NodeGenePattern pattern;

            if (nodeGenePatterns.ContainsKey(connectionGene.ConnectionGenePattern.ReplacingNumber))
            {
                pattern = nodeGenePatterns[connectionGene.ConnectionGenePattern.ReplacingNumber];
            }
            else
            {
                pattern = new NodeGenePattern(this, connectionGene.ConnectionGenePattern.ReplacingNumber,
                                              (connectionGene.ConnectionGenePattern.From.X + connectionGene.ConnectionGenePattern.To.X) / 2);

                nodeGenePatterns.Add(pattern.InnovationNumber, pattern);
            }

            return(new NodeGene(pattern, GetRandomActivationFunction()));
        }
Example #24
0
        /// <summary>
        /// Calculates Output for Genome
        /// </summary>
        /// <param name="input">Input for Genome</param>
        /// <returns>Output-Values for Genome</returns>
        public double[] Calculate(double[] input)
        {
            int output = 0;

            Profiler.BeginSample("Set up Network");
            if (inputConnectionsPerNode.Count == 0)
            {
                SetUpNetwork();
            }
            Profiler.EndSample();
            Profiler.BeginSample("CalcNodes");
            for (int i = 0; i < nodesInOrder.Count; i++)
            {
                NodeGene gene = Nodes[nodesInOrder[i]];
                if (gene.Type == NodeType.INPUT) // Input-Nodes are always at the start, as they have the lowest Innovation-Number
                {
                    gene.SetState(input[i]);
                }
                else
                {
                    List <ConnectionGene> inputs = inputConnectionsPerNode[gene];
                    double N = 0;
                    Profiler.BeginSample("HiddenNode");
                    for (int j = 0; j < inputs.Count; j++)
                    {
                        ConnectionGene conn   = inputs[j];
                        NodeGene       inNode = Nodes[conn.In.Innovation]; // Grab Node from Nodes to get proper State (We're using Structs)
                        N += conn.Weight * inNode.State;
                    }
                    Profiler.EndSample();
                    gene.SetState(Activations.Sigmoid(N));
                    if (gene.Type == NodeType.OUTPUT)
                    {
                        outputCache[output] = gene.State;
                    }
                }
            }
            Profiler.EndSample();
            return(outputCache);
        }
Example #25
0
    public Genome InitGenome()
    {
        Genome g1 = new Genome(gt);



        for (int i = 0; i < inputSize + outputSize; i++)
        {
            NodeGene node = GetDeafultGenome().GetNodeGenes()[i].Copy();
            if (node.GetNodeType() == NodeGene.NODETYPE.OUTPUT || node.GetNodeType() == NodeGene.NODETYPE.HIDDEN)
            {
                node.SetBias(Random.Range(-1.0f, 1.0f));
                //node.SetBias(1.0f);
            }
            g1.AddNodeGene(node);
            //g1.GetNodeGenes()[inputSize + i].SetBias(Random.Range(-1.0f, 1.0f));
        }
        for (int i = 0; i < startConnections; i++)//sample n connections
        {
            ConnectionGene con = connections[Random.Range(0, connections.Count)].Copy();
            //ConnectionGene con = connections[i].Copy();
            con.SetWeight(Random.Range(-weightRange, weightRange));
            //con.SetWeight(1.0f);
            int inId = con.GetInNode().GetId();
            con.SetInNode(g1.GetNodeGenes()[inId]);
            int outId = con.GetOutNode().GetId();
            //Debug.Log(con.GetOutNode());
            //Debug.Log(outId);
            con.SetOutNode(g1.GetNodeGenes()[outId]);
            g1.AddConnectionGene(con);
        }
        if (speciation)
        {
            InsertGenomeIntoSpecies(g1, species);
            impf.StatsSpecies(species.Count);
        }
        genomes.Add(g1);

        return(g1);
    }
Example #26
0
        ///<inheritdoc/>
        public void MutateLink()
        {
            for (int i = 0; i < 100; i++)
            {
                NodeGene a = Nodes.RandomElement();
                NodeGene b = Nodes.RandomElement();

                if (a == null || b == null)
                {
                    continue;
                }
                if (a.X.Equals(b.X))
                {
                    continue;
                }

                ConnectionGene connection;
                if (a.X < b.X)
                {
                    connection = new ConnectionGene(a, b);
                }
                else
                {
                    connection = new ConnectionGene(b, a);
                }

                if (Connections.Contains(connection))
                {
                    continue;
                }

                connection         = Neat.GetConnection(connection.In, connection.Out);
                connection.Weight += ThreadSafeRandom.NormalRand(0, 0.2f) * Constants.WEIGHT_SHIFT_STRENGTH;

                AddSorted(connection);

                return;
            }
        }
Example #27
0
        /// <summary>
        /// Adds Node for Random Connection in Genome (Structural Mutation)
        /// </summary>
        internal void MutateAddRandomNode()
        {
            if (Connections.Count == 0)
            {
                throw new InvalidOperationException("No existing connections");
            }
            // Find a random (expressed) connection
            List <ConnectionGene> conns = Connections.Values.ToList();

            for (int i = 0; i < MaxFindAttempts; i++) // Try x times max
            {
                int            randomIndex = Functions.GetRandomNumber(0, Connections.Count);
                ConnectionGene conn        = conns[randomIndex];
                if (!conn.Expressed)
                {
                    continue;        // Connection is not active
                }
                MutateAddNode(conn); // Add Node for Connection
                return;              // Break out (solution found)
            }
            Console.WriteLine("Failed to add Node");
        }
Example #28
0
    public void AddNodeMutation(Random r)                                     //insert a node between two connected nodes
    {
        int            conKey = connectionKeys[r.Next(connectionKeys.Count)]; //get a random connection
        ConnectionGene con    = connectionList[conKey];
        int            node1  = con.GetInNode();
        int            node2  = con.GetOutNode();

        con.Disable();                                                                 //disable connection

        NodeGene newNode = new NodeGene(nodeList.Count + 1, NodeGene.TYPE.HIDDEN);     //create a new node

        nodeList.Add(newNode);                                                         //add new node to node list

        int innovation1 = InnovationGenerator.GetInnovation();
        int innovation2 = InnovationGenerator.GetInnovation();

        connectionKeys.Add(innovation1);
        connectionList.Add(innovation1, new ConnectionGene(node1, newNode.GetID(), 1f, true, innovation1));    //add new connections to connection list

        connectionKeys.Add(innovation2);
        connectionList.Add(innovation2, new ConnectionGene(newNode.GetID(), node2, con.GetWeight(), true, innovation2));
    }
Example #29
0
        public void Distance_TwoNodes_1Connection_DifferentWeight_2to1()
        {
            if (!Genome.IsInitialized())
            {
                Genome.Init();
            }


            NodeGene nodeGene_1 = new NodeGene(1, Node.INPUT_X, Neural_Network.Node.Sigmoid);
            NodeGene nodeGene_2 = new NodeGene(2, Node.OUTPUT_X, Neural_Network.Node.Sigmoid);

            NodeGene nodeGene_3 = new NodeGene(1, Node.INPUT_X, Neural_Network.Node.Sigmoid);
            NodeGene nodeGene_4 = new NodeGene(2, Node.OUTPUT_X, Neural_Network.Node.Sigmoid);

            ConnectionGene connectionGene_1 = new ConnectionGene(nodeGene_1, nodeGene_2, 1);
            ConnectionGene connectionGene_2 = new ConnectionGene(nodeGene_3, nodeGene_4, 2);


            Random random = new Random();

            Genome genome_1 = new Genome(random);

            genome_1.NodeGenes.Add(nodeGene_1.InnovationNumber, nodeGene_1);
            genome_1.NodeGenes.Add(nodeGene_2.InnovationNumber, nodeGene_2);

            genome_1.ConnectionGenes.Add(connectionGene_1.InnovationNumber, connectionGene_1);


            Genome genome_2 = new Genome(random);

            genome_2.NodeGenes.Add(nodeGene_3.InnovationNumber, nodeGene_3);
            genome_2.NodeGenes.Add(nodeGene_4.InnovationNumber, nodeGene_4);

            genome_2.ConnectionGenes.Add(connectionGene_2.InnovationNumber, connectionGene_2);


            Assert.AreEqual(Genome.C3 * 1, genome_2.Distance(genome_1));
        }
Example #30
0
    public void MutateAddNode()
    {
        ConnectionGene randomConnection = GetConnectionGenes()[random.Next(GetConnectionGenes().Count)];

        NodeGene InNode  = GetNodeGenes()[randomConnection.GetInputNode()];
        NodeGene OutNode = GetNodeGenes()[randomConnection.GetOutputNode()];


        randomConnection.SetEnabled(false);

        NodeGene MiddleNode = new NodeGene(GetNodeGenes().Count + 1, NodeGene.TYPE.HIDDEN, 0);

        ConnectionGene InputToMiddle = new ConnectionGene(InNode.GetID(), MiddleNode.GetID(), 1, true, NEAT_CONFIGS.GLOBAL_INNOVATION_NUMBER++);

        ConnectionGenes.Add(InputToMiddle);
        MiddleNode.AddIncomingConnection(InputToMiddle);
        ConnectionGene MiddleToOutput = new ConnectionGene(MiddleNode.GetID(), OutNode.GetID(), randomConnection.GetWeight(), true, NEAT_CONFIGS.GLOBAL_INNOVATION_NUMBER++);

        ConnectionGenes.Add(MiddleToOutput);
        OutNode.AddIncomingConnection(MiddleToOutput);
        //Add to the total current Pool Connections Made in this instance
        NodeGenes.Add(MiddleNode.GetID(), MiddleNode);
    }
        private static void WriteConnectionGene(XmlElement xmlConnections, ConnectionGene connectionGene)
        {
            XmlElement xmlConnectionGene = XmlUtilities.AddElement(xmlConnections, "connection");

            XmlUtilities.AddAttribute(xmlConnectionGene, "innov-id", connectionGene.InnovationId.ToString());
            XmlUtilities.AddAttribute(xmlConnectionGene, "src-id", connectionGene.SourceNeuronId.ToString());
            XmlUtilities.AddAttribute(xmlConnectionGene, "tgt-id", connectionGene.TargetNeuronId.ToString());
            XmlUtilities.AddAttribute(xmlConnectionGene, "weight", connectionGene.Weight.ToString("R"));
            XmlUtilities.AddAttribute(xmlConnectionGene, "learningrate", connectionGene.learningRate.ToString("R"));
            XmlUtilities.AddAttribute(xmlConnectionGene, "A", connectionGene.A.ToString("R"));
            XmlUtilities.AddAttribute(xmlConnectionGene, "B", connectionGene.B.ToString("R"));
            XmlUtilities.AddAttribute(xmlConnectionGene, "C", connectionGene.C.ToString("R"));
            XmlUtilities.AddAttribute(xmlConnectionGene, "D", connectionGene.D.ToString("R"));
        }
 /// <summary>
 /// Constructs a new CorrelationItem.
 /// </summary>
 public CorrelationItem(CorrelationItemType correlationItemType, ConnectionGene connectionGene1, ConnectionGene connectionGene2)
 {
     _correlationItemType = correlationItemType;
     _connectionGene1 = connectionGene1;
     _connectionGene2 = connectionGene2;
 }