30 #ifndef MODELS_NEURONS_H 31 #define MODELS_NEURONS_H 48 noalias(arg) = tanh(arg);
56 template<
class Output,
class Derivative>
58 noalias(der) *=
typename Output::value_type(1) -
sqr(output);
80 template<
class Output,
class Derivative>
82 noalias(der) *= output * (
typename Output::value_type(1) - output);
96 noalias(arg) /=
typename Arg::value_type(1)+abs(arg);
104 template<
class Output,
class Derivative>
106 noalias(der) *=
sqr(
typename Output::value_type(1) - abs(output));
119 template<
class Output,
class Derivative>
128 noalias(arg) = max(arg,
typename Arg::value_type(0));
136 template<
class Output,
class Derivative>
139 for(std::size_t i = 0; i != output.size1(); ++i){
140 for(std::size_t j = 0; j != output.size2(); ++j){
141 der(i,j) *= output(i,j) > 0? 1.0:0.0;
147 template<
class VectorType = RealVector>
153 norm.resize(patterns);
157 template<
class Arg,
class Device>
159 noalias(arg) /= sum(arg);
162 template<
class Arg,
class Device>
164 noalias(trans(arg)) /= blas::repeat(sum_columns(arg),arg().size2());
167 template<
class Arg,
class Device>
169 state.
norm.resize(arg().size1());
170 noalias(state.
norm) = sum_columns(arg);
171 noalias(arg) /= trans(blas::repeat(state.
norm,arg().size2()));
174 template<
class Output,
class Derivative>
176 for(std::size_t i = 0; i != output.size1(); ++i){
177 double constant=inner_prod(row(der,i),row(output,i));
178 noalias(row(der,i))= (row(der,i)-constant)/s.
norm(i);
184 template<
class VectorType = RealVector>
188 template<
class Arg,
class Device>
190 noalias(arg) = exp(arg);
191 noalias(arg) /= sum(arg);
194 template<
class Arg,
class Device>
196 noalias(arg) = exp(arg);
197 noalias(arg) /= trans(blas::repeat(sum_columns(arg),arg().size2()));
200 template<
class Arg,
class Device>
201 void evalInPlace(blas::matrix_expression<Arg,Device>& arg, State&)
const{
205 template<
class Output,
class Derivative>
207 for(
size_t i = 0; i != output.size1(); ++i){
208 double mass=inner_prod(row(der,i),row(output,i));
209 noalias(row(der,i)) = (row(der,i) - mass) *row(output,i);
214 template <
class NeuronType,
class VectorType = RealVector>
227 base_type::m_features |= base_type::HAS_FIRST_PARAMETER_DERIVATIVE;
228 base_type::m_features |= base_type::HAS_FIRST_INPUT_DERIVATIVE;
233 {
return "NeuronLayer"; }
235 NeuronType
const&
neuron()
const{
return m_neuron;}
248 return ParameterVectorType();
262 return boost::shared_ptr<State>(
new typename NeuronType::State());
265 using base_type::eval;
267 void eval(BatchInputType
const& inputs, BatchOutputType& outputs)
const{
269 outputs.resize(inputs.size1(),inputs.size2());
270 noalias(outputs) = inputs;
271 m_neuron.evalInPlace(outputs);
276 output.resize(input.size());
277 noalias(output) = input;
278 m_neuron.evalInPlace(output);
280 void eval(BatchInputType
const& inputs, BatchOutputType& outputs,
State& state)
const{
282 outputs.resize(inputs.size1(),inputs.size2());
283 noalias(outputs) = inputs;
284 m_neuron.evalInPlace(outputs, state.
toState<
typename NeuronType::State>());
289 BatchInputType
const& inputs,
290 BatchOutputType
const& outputs,
291 BatchOutputType
const& coefficients,
293 ParameterVectorType& gradient
295 SIZE_CHECK(coefficients.size1()==inputs.size1());
296 SIZE_CHECK(coefficients.size2()==inputs.size2());
300 BatchInputType
const & inputs,
301 BatchOutputType
const & outputs,
302 BatchOutputType
const & coefficients,
304 BatchInputType& derivative
306 SIZE_CHECK(coefficients.size1() == inputs.size1());
307 SIZE_CHECK(coefficients.size2() == inputs.size2());
309 derivative.resize(inputs.size1(),inputs.size2());
310 noalias(derivative) = coefficients;
311 m_neuron.multiplyDerivative(outputs, derivative, state.
toState<
typename NeuronType::State>());