示例#1
0
 /// <summary>
 /// Clones the neuron
 /// </summary>
 /// <param name="neuron"></param>
 public Neuron(Neuron neuron)
 {
     _weights = new List <double>(neuron._weights);
 }
示例#2
0
 public Weight(Neuron input, double value)
 {
     this.inputNeuron = input;
     this.value       = value;
 }
示例#3
0
 public Link(double value, Neuron source)
 {
     Value = value;
     SourceNeuron = source;
 }
 public void AddLink(double value, Neuron source)
 {
     Links.Add(new Link(value, source));
 }
示例#5
0
        /// <summary>
        /// Creates the network.
        /// </summary>
        /// <param name="NeuronsAndLayers">The struct of the network. For instance, "4+ 15+ 5 3" whare '+' means bias. Watch readme</param>
        /// <param name="randMin">Minimal random weight of synapse.</param>
        /// <param name="randMax">Maximal random weight of synapse.</param>
        public NeuralNetwork(string NeuronsAndLayers, double randMin, double randMax)
        {
            Random rand = new Random();

            string[] neuronsSTR = NeuronsAndLayers?.Split(' ');
            Network           = new Neuron[neuronsSTR.Length][];
            withoutBiasLength = new uint[neuronsSTR.Length];
            System.Collections.ArrayList biases = new System.Collections.ArrayList();
            for (i = 0; i < neuronsSTR.Length; ++i) //Count of neurons in each layer
            {
                try                                 //Check if there are biases
                {
                    uint index = Convert.ToUInt32(neuronsSTR[i]);
                    Network[i]           = new Neuron[index];
                    withoutBiasLength[i] = index;
                }
                catch (Exception) //If bias is in the layer then
                {
                    if (i == neuronsSTR.Length - 1)
                    {
                        throw new Exception("You cannot add biases to OUTPUT layers");
                    }
                    else
                    {
                        biases.Add(i);
                        uint index = Convert.ToUInt32(neuronsSTR[i].Substring(0, neuronsSTR[i].Length - 1)) + 1;
                        Network[i] = new Neuron[index]; //Convert only count of neurons without bias(+)
                        Network[i][index - 1].value = 1;
                        withoutBiasLength[i]        = index - 1;
                    }
                }
            }

            previousWeights = new double[Network.Length][];
            //Distribution of values in weights of Neural Network and initializing PreviousWeights
            for (i = 0; i < Network.Length - 1; ++i) //             Every layer in this NeuralNetwork
            {
                previousWeights[i] = new double[Network[i].Length * withoutBiasLength[i + 1]];
                uint countOfWeights = 0;

                for (j = 0; j < Network[i].Length; ++j) //          Every neuron in layer[i]
                {
                    Network[i][j].weights = new double[withoutBiasLength[i + 1]];
                    for (uint a = 0; a < Network[i][j].weights.Length; ++a) // Every weight from neuron[i][j]
                    {
                        previousWeights[i][countOfWeights] = 0;             //PrewiosWeight on the first iteration = 0
                        ++countOfWeights;

weightWasZeroREPEAT:
                        Network[i][j].weights[a] = Math.Round(rand.NextDouble() * (randMax - randMin) + randMin, 5); //Random value for the weight
                        if (Network[i][j].weights[a] == 0)
                        {
                            goto weightWasZeroREPEAT; //Value of weight cannot be 0
                        }
                    }
                }
            }

            //Creating a copy of NeuralNetwork to work with it
            deltaNetwork = new Neuron[Network.Length][];
            for (i = 0; i < Network.Length; ++i)
            {
                deltaNetwork[i] = new Neuron[Network[i].Length];
                for (j = 0; j < Network[i].Length; ++j)
                {
                    deltaNetwork[i][j] = Network[i][j];
                }
            }
        }
示例#6
0
        private static void train()
        {
            double[,] inputs =
            {
                { 1, 1, 0 },
                { 1, 0, 1 },
                { 0, 1, 1 },
                { 0, 1, 0 },
                { 0, 1, 1 },
                { 0, 0, 1 },
                { 0, 1, 0 },
                { 1, 1, 1 },
                { 0, 0, 0 }
            };

            // desired results
            double[] results = { 1, 1, 2, 3, 2, 3, 3, 1, 2 };

            double max = -1;

            // find max value
            for (int i = 0; i < results.Length; i++)
            {
                if (results[i] > max)
                {
                    max = results[i];
                }
            }

            // normalizing
            for (int i = 0; i < results.Length; i++)
            {
                results[i] /= max;
            }

            // creating the neurons
            List <Neuron> hiddenNeurons = new List <Neuron>(numberOfneurons);

            for (int i = 0; i < numberOfneurons; i++)
            {
                hiddenNeurons.Add(new Neuron());
            }

            Neuron outputNeuron = new Neuron();

            // random weights
            foreach (Neuron hiddenNeuron in hiddenNeurons)
            {
                hiddenNeuron.randomizeWeights();
            }

            outputNeuron.randomizeWeights();

            int epoch = 0;

Retry:
            epoch++;
            for (int i = 0; i < inputs.GetLength(0); i++)
            {
                // 1) forward propagation (calculates output)
                outputNeuron.inputs = fillIN(inputs[i, 0], inputs[i, 1], inputs[i, 2], hiddenNeurons);

                Console.WriteLine("{0} and {1} and {2} = {3}", inputs[i, 0], inputs[i, 1], inputs[i, 2], outputNeuron.output * numberOfneurons);

                // 2) back propagation (adjusts weights)

                // adjusts the weight of the output neuron, based on its error
                outputNeuron.error = sigmoid.derivative(outputNeuron.output) * (results[i] - outputNeuron.output);
                outputNeuron.adjustWeights();

                // then adjusts the hidden neurons' weights, based on their errors
                for (int j = 0; j < numberOfneurons; j++)
                {
                    hiddenNeurons[j].error = sigmoid.derivative(hiddenNeurons[j].output) * outputNeuron.error * outputNeuron.weights[j];
                }

                foreach (Neuron hiddenNeuron in hiddenNeurons)
                {
                    hiddenNeuron.adjustWeights();
                }
            }

            if (epoch < 10000)
            {
                goto Retry;
            }

            Console.WriteLine();
            Console.WriteLine("Network have been trained successfully");

            while (true)
            {
                Console.WriteLine("________________________");
                Console.WriteLine("Print your binary values");

                Console.Write("value 1: ");
                int value1 = Convert.ToInt32(Console.ReadLine());

                Console.Write("value 2: ");
                int value2 = Convert.ToInt32(Console.ReadLine());

                Console.Write("value 3: ");
                int value3 = Convert.ToInt32(Console.ReadLine());

                outputNeuron.inputs = fillIN(value1, value2, value3, hiddenNeurons);

                Console.WriteLine("result : " + (outputNeuron.output * max).ToString("0"));
            }
        }