cascade correlation implementation
This commit is contained in:
@@ -10,9 +10,10 @@
|
||||
namespace NeuralNetwork {
|
||||
namespace ConstructiveAlgorihtms {
|
||||
class CascadeCorrelation {
|
||||
typedef std::pair<std::vector<float>, std::vector<float>> TrainingPattern;
|
||||
public:
|
||||
CascadeCorrelation(std::size_t numberOfCandidate = 20, float maxError = 0.7) :
|
||||
typedef std::pair<std::vector<float>, std::vector<float>> TrainingPattern;
|
||||
|
||||
CascadeCorrelation(std::size_t numberOfCandidate = 18, float maxError = 0.7) :
|
||||
_maxError(maxError), _weightRange(0.3), _numberOfCandidates(numberOfCandidate), _generator(rand()), _distribution() {
|
||||
setWeightRange(_weightRange);
|
||||
}
|
||||
@@ -25,19 +26,27 @@ namespace NeuralNetwork {
|
||||
|
||||
network.randomizeWeights();
|
||||
|
||||
std::size_t step = 0;
|
||||
float error = trainOutputs(network, patterns);
|
||||
while(step++ < _maxHiddenUnits && error > _maxError) {
|
||||
_epoch = 0;
|
||||
float error;
|
||||
if(_useProbabilisticOutputWeightSearch) {
|
||||
error = trainOutputsRandom(0, network, patterns);
|
||||
} else {
|
||||
error = trainOutputs(network, patterns);
|
||||
}
|
||||
while(_epoch++ < _maxHiddenUnits && error > _maxError) {
|
||||
std::vector<std::shared_ptr<Neuron>> candidates = createCandidates(network.getNeuronSize() - outputs);
|
||||
|
||||
std::pair<std::shared_ptr<Neuron>, std::vector<float>> candidate = trainCandidates(network, candidates, patterns);
|
||||
|
||||
addBestCandidate(network, candidate);
|
||||
|
||||
error = trainOutputs(network, patterns);
|
||||
if(_useProbabilisticOutputWeightSearch) {
|
||||
error = trainOutputsRandom(0, network, patterns);
|
||||
} else {
|
||||
error = trainOutputs(network, patterns);
|
||||
}
|
||||
}
|
||||
|
||||
std::cout << step << ": " << error << "\n";
|
||||
|
||||
return network;
|
||||
}
|
||||
|
||||
@@ -66,13 +75,34 @@ namespace NeuralNetwork {
|
||||
_activFunction = std::shared_ptr<ActivationFunction::ActivationFunction>(function.clone());
|
||||
}
|
||||
|
||||
void setProbabilisticOutputWeightSearch(bool status) {
|
||||
_useProbabilisticOutputWeightSearch = status;
|
||||
}
|
||||
|
||||
bool getProbabilisticOutputWeightSearch() const {
|
||||
return _useProbabilisticOutputWeightSearch;
|
||||
}
|
||||
|
||||
std::size_t getEpochs() const {
|
||||
return _epoch;
|
||||
}
|
||||
|
||||
protected:
|
||||
std::shared_ptr<ActivationFunction::ActivationFunction> _activFunction = std::make_shared<ActivationFunction::Sigmoid>(-4.9);
|
||||
float _minimalErrorStep = 0.00005;
|
||||
float _maxError;
|
||||
float _weightRange;
|
||||
bool _useProbabilisticOutputWeightSearch = false;
|
||||
|
||||
std::size_t _epoch = 0;
|
||||
std::size_t _maxHiddenUnits = 20;
|
||||
std::size_t _maxRandomOutputWeights = 20;
|
||||
std::size_t _numberOfCandidates;
|
||||
std::size_t _maxOutpuLearningIterations = 1000;
|
||||
std::size_t _maxOutpuLearningIterationsWithoutChange = 5;
|
||||
std::size_t _maxCandidateIterations = 20;
|
||||
std::size_t _maxCandidateIterationsWithoutChange = 5;
|
||||
|
||||
std::mt19937 _generator;
|
||||
std::uniform_real_distribution<> _distribution;
|
||||
private:
|
||||
@@ -93,6 +123,8 @@ namespace NeuralNetwork {
|
||||
|
||||
float trainOutputs(Cascade::Network &network, const std::vector<TrainingPattern> &patterns);
|
||||
|
||||
float trainOutputsRandom(std::size_t step, Cascade::Network &network, const std::vector<TrainingPattern> &patterns);
|
||||
|
||||
std::pair<std::shared_ptr<Neuron>, std::vector<float>> trainCandidates(Cascade::Network &network, std::vector<std::shared_ptr<Neuron>> &candidates,
|
||||
const std::vector<TrainingPattern> &patterns);
|
||||
|
||||
@@ -106,9 +138,9 @@ namespace NeuralNetwork {
|
||||
for(auto &n :network.getOutputNeurons()) {
|
||||
auto weights = n->getWeights();
|
||||
for(auto &weight: weights) {
|
||||
weight *= 0.7;
|
||||
weight *= 0.9;
|
||||
}
|
||||
weights[weights.size() - 1] = -candidate.second[outIndex] * weightPortion;//_distribution(_generator);
|
||||
weights[weights.size() - 1] = -candidate.second[outIndex] / weightPortion;//_distribution(_generator);
|
||||
outIndex++;
|
||||
n->setWeights(weights);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user