1 //   OpenNN: Open Neural Networks Library
2 //   www.opennn.net
3 //
4 //   P E R C E P T R O N   L A Y E R   C L A S S   H E A D E R
5 //
6 //   Artificial Intelligence Techniques SL
7 //   artelnics@artelnics.com
8 
9 #ifndef PERCEPTRONLAYER_H
10 #define PERCEPTRONLAYER_H
11 
12 // System includes
13 
14 #include <cmath>
15 #include <cstdlib>
16 #include <fstream>
17 #include <iostream>
18 #include <string>
19 #include <sstream>
20 
21 // OpenNN includes
22 
23 #include "config.h"
24 #include "layer.h"
25 #include "probabilistic_layer.h"
26 #include "opennn_strings.h"
27 
28 namespace OpenNN
29 {
30 
31 /// This class represents a layer of perceptrons.
32 
33 /// PerceptronLayer is a single-layer network with a hard-limit trabsfer function.
34 /// This network is often trained with the perceptron learning rule.
35 ///
36 /// Layers of perceptrons will be used to construct multilayer perceptrons, such as an approximation problems .
37 
38 class PerceptronLayer : public Layer
39 {
40 
41 public:
42 
43     /// Enumeration of available activation functions for the perceptron neuron model.
44 
45     enum ActivationFunction{Threshold, SymmetricThreshold, Logistic, HyperbolicTangent, Linear, RectifiedLinear,
46                             ExponentialLinear, ScaledExponentialLinear, SoftPlus, SoftSign, HardSigmoid};
47 
48     enum PerceptronLayerType{HiddenLayer, OutputLayer};
49 
50    // Constructors
51 
52    explicit PerceptronLayer();
53 
54    explicit PerceptronLayer(const Index&, const Index&, const Index& = 0 , const ActivationFunction& = PerceptronLayer::HyperbolicTangent);
55 
56    // Destructor
57 
58    virtual ~PerceptronLayer();
59 
60    // Get methods
61 
62    bool is_empty() const;
63 
64    Index get_inputs_number() const;
65    Index get_neurons_number() const;
66 
67    // Parameters
68 
69    const Tensor<type, 2>& get_biases() const;
70    const Tensor<type, 2>& get_synaptic_weights() const;
71 
72    Tensor<type, 2> get_biases(const Tensor<type, 1>&) const;
73    Tensor<type, 2> get_synaptic_weights(const Tensor<type, 1>&) const;
74 
75    Index get_biases_number() const;
76    Index get_synaptic_weights_number() const;
77    Index get_parameters_number() const;
78    Tensor<type, 1> get_parameters() const;
79 
80    // Activation functions
81 
82    const PerceptronLayer::ActivationFunction& get_activation_function() const;
83 
84    string write_activation_function() const;
85 
86    // Display messages
87 
88    const bool& get_display() const;
89 
90    // Set methods
91 
92    void set();
93    void set(const Index&, const Index&, const PerceptronLayer::ActivationFunction& = PerceptronLayer::HyperbolicTangent);
94 
95    void set_default();
96    void set_layer_name(const string&);
97 
98    // Architecture
99 
100    void set_inputs_number(const Index&);
101    void set_neurons_number(const Index&);
102 
103    // Parameters
104 
105    void set_biases(const Tensor<type, 2>&);
106    void set_synaptic_weights(const Tensor<type, 2>&);
107 
108    void set_parameters(const Tensor<type, 1>&, const Index& index=0);
109 
110    // Activation functions
111 
112    void set_activation_function(const ActivationFunction&);
113    void set_activation_function(const string&);
114 
115    // Display messages
116 
117    void set_display(const bool&);
118 
119    // Parameters initialization methods
120    void set_biases_constant(const type&);
121    void set_synaptic_weights_constant(const type&);
122    void set_synaptic_weights_glorot();
123 
124    void set_parameters_constant(const type&);
125 
126    void set_parameters_random();
127 
128    // Perceptron layer combinations_2d
129 
130    void calculate_combinations(const Tensor<type, 2>& inputs,
131                                const Tensor<type, 2>& biases,
132                                const Tensor<type, 2>& synaptic_weights,
133                                Tensor<type, 2>& combinations_2d) const;
134 
135    // Perceptron layer activations_2d
136 
137    void calculate_activations(const Tensor<type, 2>& combinations_2d, Tensor<type, 2>& activations_2d) const;
138 
139    void calculate_activations_derivatives(const Tensor<type, 2>& combinations_2d,
140                                           Tensor<type, 2>& activations,
141                                           Tensor<type, 2>& activations_derivatives) const;
142 
143    // Perceptron layer outputs
144 
145    Tensor<type, 2> calculate_outputs(const Tensor<type, 2>&);
146 
147 
148    void forward_propagate(const Tensor<type, 2>& inputs,
149                                       ForwardPropagation& forward_propagation) const;
150 
151 
152    void forward_propagate(const Tensor<type, 2>& inputs,
153                                       Tensor<type, 1> potential_parameters,
154                                       ForwardPropagation& forward_propagation) const;
155 
156    // Delta methods
157 
158    void calculate_output_delta(ForwardPropagation& forward_propagation,
159                                   const Tensor<type, 2>& output_gradient,
160                                   Tensor<type, 2>& output_delta) const;
161 
162    void calculate_hidden_delta(Layer* next_layer_pointer,
163                                const Tensor<type, 2>&,
164                                ForwardPropagation& forward_propagation,
165                                const Tensor<type, 2>& next_layer_delta,
166                                Tensor<type, 2>& hidden_delta) const;
167 
168    void calculate_hidden_delta_perceptron(Layer* next_layer_pointer,
169                                           const Tensor<type, 2>& activations_derivatives,
170                                           const Tensor<type, 2>& next_layer_delta,
171                                           Tensor<type, 2>& hidden_delta) const;
172 
173    void calculate_hidden_delta_probabilistic(Layer* next_layer_pointer,
174                                              const Tensor<type, 2>& activations_derivatives,
175                                              const Tensor<type, 2>& next_layer_delta,
176                                              Tensor<type, 2>& hidden_delta) const;
177 
178    // Gradient methods
179 
180    void calculate_error_gradient(const Tensor<type, 2>& inputs,
181                                  const Layer::ForwardPropagation&,
182                                  Layer::BackPropagation& back_propagation) const;
183 
184    void insert_gradient(const BackPropagation& back_propagation, const Index& index, Tensor<type, 1>& gradient) const;
185 
186    // Expression methods
187 
188    string write_expression(const Tensor<string, 1>&, const Tensor<string, 1>&) const;
189 
190    string write_hidden_layer_expression(const Tensor<string, 1>&, const Tensor<string, 1>&) const;
191    string write_output_layer_expression(const Tensor<string, 1>&, const Tensor<string, 1>&) const;
192 
193    string write_activation_function_expression() const;
194 
195    string write_expression_c() const;
196    string write_combinations_c() const;
197    string write_activations_c() const;
198 
199    string write_combinations_python() const;
200    string write_activations_python() const;
201    string write_expression_python() const;
202 
203    // Serialization methods
204 
205    void from_XML(const tinyxml2::XMLDocument&);
206    void write_XML(tinyxml2::XMLPrinter&) const;
207 
208 protected:
209 
210    // MEMBERS
211 
212    /// Bias is a neuron parameter that is summed with the neuron's weighted inputs
213    /// and passed through the neuron's transfer function to generate the neuron's output.
214 
215    Tensor<type, 2> biases;
216 
217    /// This matrix containing conection strengths from a layer's inputs to its neurons.
218 
219    Tensor<type, 2> synaptic_weights;
220 
221    /// Activation function variable.
222 
223    ActivationFunction activation_function;
224 
225    /// Layer type variable.
226 
227    PerceptronLayerType perceptron_layer_type = OutputLayer;
228 
229    /// Display messages to screen.
230 
231    bool display = true;
232 
233 #ifdef OPENNN_CUDA
234     #include "../../opennn-cuda/opennn_cuda/perceptron_layer_cuda.h"
235 #endif
236 
237 #ifdef OPENNN_MKL
238     #include"../../opennn-mkl/opennn_mkl/perceptron_layer_mkl.h"
239 #endif
240 };
241 
242 }
243 
244 #endif
245 
246 
247 // OpenNN: Open Neural Networks Library.
248 // Copyright(C) 2005-2020 Artificial Intelligence Techniques, SL.
249 //
250 // This library is free software; you can redistribute it and/or
251 // modify it under the terms of the GNU Lesser General Public
252 // License as published by the Free Software Foundation; either
253 // version 2.1 of the License, or any later version.
254 //
255 // This library is distributed in the hope that it will be useful,
256 // but WITHOUT ANY WARRANTY; without even the implied warranty of
257 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
258 // Lesser General Public License for more details.
259 
260 // You should have received a copy of the GNU Lesser General Public
261 // License along with this library; if not, write to the Free Software
262 
263 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
264