⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 net.cs

📁 股票预测的程序
💻 CS
字号:
using System;
using System.Collections.Generic;
using System.Text;

namespace NeuralNetCS
{
    class Net
    {
        private double[] _examples;
        private Node[] _input;
        private Node[] _hidden;
        private Node _output;
        private double _learningRate;

        /// <summary>
        /// Initializes a new instance of the Net class.
        /// </summary>
        /// <param name="hiddenNodeCount">The number of nodes, not including the bias node, in the hidden layer.</param>
        /// <param name="learningRate"></param>
        /// <param name="examples"></param>
        public Net(int hiddenNodeCount, double learningRate, double[] examples)
        {
            if( hiddenNodeCount <= 0 )
                throw new ArgumentException("The net needs at least one hidden node.", "hiddenNodeCount");
            if( learningRate <= 0 )
                throw new ArgumentException("The learning rate must be larger than zero.", "learningRate");
            if( examples == null )
                throw new ArgumentNullException("examples");
            if( examples.Length == 0 )
                throw new ArgumentException("No examples specified.", "examples");

            _examples = examples;
            _learningRate = learningRate;

            // Create the input layer: one bias node and one input node.
            _input = new Node[2];
            _input[0] = new Node(-1.0f); // Bias node
            _input[1] = new Node(0);

            // Create the hidden layer, using one bias node.
            _hidden = new Node[hiddenNodeCount + 1];
            _hidden[0] = new Node(-1.0f); // Bias node
            for( int x = 1; x < _hidden.Length; ++x )
                _hidden[x] = new Node(_input);

            // Create the output layer
            _output = new Node(_hidden);

        }

        /// <summary>
        /// Execute the learning algorithm, and write the final net output to a file.
        /// </summary>
        /// <param name="epochs">The number of epochs to use when learning.</param>
        /// <param name="outputFile">The output file name.</param>
        public void Learn(uint epochs, string outputFile)
        {
            if( outputFile == null )
                throw new ArgumentNullException("outputFile");
            if( epochs <= 0 )
                throw new ArgumentException("The number of epochs must be larger than zero.", "epochs");

            BackPropLearning(epochs);
            OutputNet(outputFile);
        }

        /// <summary>
        /// Evaluates the entire network.
        /// </summary>
        private void EvalNet()
        {
            // Evaluate hidden layer, all but the bias node.
            int length = _hidden.Length;
            for( int x = 1; x < length; ++x )
                _hidden[x].Eval();
            // Evaluate the output layer
            _output.Eval();
        }

        /// <summary>
        /// Trains the net using the example data, using the back-propagation learning algorithm.
        /// </summary>
        /// <param name="epochs">The number of epochs to use when learning.</param>
        private void BackPropLearning(uint epochs)
        {
            double[] hiddenDelta = new double[_hidden.Length];

            int examplesLength = _examples.Length;
            int hiddenLength = _hidden.Length;
            int inputLength = _input.Length;
            for( uint epoch = 1; epoch <= epochs; ++epoch )
            {
                double totalError = 0;
                bool computeError = epoch % 1000 == 0 || epoch == epochs || epoch == 1;

                for( int input = 0; input < examplesLength; ++input )
                {
                    // Set the input
                    _input[1].Value = input / 100.0f;
                    // Forward pass: evaluate the network
                    EvalNet();

                    if( computeError )
                        totalError += Math.Pow(_examples[input] - _output.Value, 2);

                    // Backward pass: update the weights
                    double outputDelta = SigmoidDerived(_output.LastInput) * (_examples[input] - _output.Value);
                    for( int x = 0; x < hiddenLength; ++x )
                    {
                        hiddenDelta[x] = SigmoidDerived(_hidden[x].LastInput) * _output.GetWeigth(x) * outputDelta;
                        _output.SetWeight(x, _output.GetWeigth(x) + _learningRate * _hidden[x].Value * outputDelta);
                    }
                    for( int x = 0; x < inputLength; ++x )
                    {
                        // No point computing the delta, it won't be used
                        for( int y = 1; y < hiddenLength; ++y )
                            _hidden[y].SetWeight(x, _hidden[y].GetWeigth(x) + _learningRate * _input[x].Value * hiddenDelta[y]);
                    }
                }
                if( computeError )
                    Console.Write("\rEpoch: {0}; Sum of squared errors: {1}        ", epoch, totalError / 2);
            }
        }

        /// <summary>
        /// Outputs the net to a file in a format that can be used by gnuplot.
        /// </summary>
        /// <param name="outputFile">The output file name</param>
        private void OutputNet(string outputFile)
        {
            using( System.IO.StreamWriter writer = new System.IO.StreamWriter(outputFile) )
            {
                for( int x = 0; x < _examples.Length; ++x )
	            {
		            _input[1].Value = x / 100.0f;
		            EvalNet();
                    // Couldn't find a way to set the formatprovider for the StreamWriter, so using String.Format
                    // instead.
                    writer.WriteLine(String.Format(System.Globalization.CultureInfo.InvariantCulture, "{0:0.######}\t{1:0.######}", _input[1].Value, _output.Value));
	            }
            }
        }

        /// <summary>
        /// The node activation function.
        /// </summary>
        /// <param name="input">The input.</param>
        /// <returns>The result of the function.</returns>
        public static double Sigmoid(double input)
        {
            return 1.0f / (1.0f + Math.Exp(-1.0f * input));
        }

        /// <summary>
        /// The first derivative of the node activiation function.
        /// </summary>
        /// <param name="input">The input.</param>
        /// <returns>The result of the function.</returns>
        public static double SigmoidDerived(double input)
        {
            return Sigmoid(input) * (1 - Sigmoid(input));
        }
    }
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -