Program Listing for File EfficientSymbiont.h¶
↰ Return to documentation for file (source/efficient_mode/EfficientSymbiont.h
)
#ifndef EFFSYM_H
#define EFFSYM_H
#include "../default_mode/Symbiont.h"
#include "EfficientWorld.h"
#include "EfficientHost.h"
class EfficientSymbiont: public Symbiont {
protected:
double efficiency;
double ht_mut_size = 0.002;
double ht_mut_rate = 0;
double eff_mut_rate = 0;
emp::Ptr<EfficientWorld> my_world = NULL;
public:
EfficientSymbiont(emp::Ptr<emp::Random> _random, emp::Ptr<EfficientWorld> _world, emp::Ptr<SymConfigBase> _config, double _intval=0.0, double _points = 0.0, double _efficient = 0.1) : Symbiont(_random, _world, _config, _intval, _points) {
efficiency = _efficient;
my_world = _world;
if(my_config->HORIZ_MUTATION_RATE() < 0){
ht_mut_rate = my_config->MUTATION_RATE();
} else {
ht_mut_rate = my_config->HORIZ_MUTATION_RATE();
}
if(my_config->HORIZ_MUTATION_SIZE() < 0) {
ht_mut_size = my_config->MUTATION_SIZE();
} else {
ht_mut_size = my_config->HORIZ_MUTATION_SIZE();
}
}
EfficientSymbiont(const EfficientSymbiont &) = default;
EfficientSymbiont(EfficientSymbiont &&) = default;
EfficientSymbiont() = default;
std::string const GetName() {
return "EfficientSymbiont";
}
void SetEfficiency(double _in) {
if(_in > 1 || _in < 0) throw "Invalid efficiency chance. Must be between 0 and 1 (inclusive)";
efficiency = _in;
}
double GetEfficiency() {return efficiency;}
void AddPoints(double _in) {points += (_in * efficiency);}
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Woverloaded-virtual"
void Mutate(std::string mode){
double local_size;
double local_rate;
double int_rate;
if(mode == "vertical"){
local_rate = my_config->MUTATION_RATE();
local_size = my_config->MUTATION_SIZE();
} else if(mode == "horizontal") {
local_rate = ht_mut_rate;
local_size = ht_mut_size;
} else {
throw "Illegal argument passed to mutate in EfficientSymbiont";
}
if(my_config->EFFICIENCY_MUT_RATE() >= 0) {
eff_mut_rate = my_config->EFFICIENCY_MUT_RATE();
} else {
eff_mut_rate = local_rate;
}
if(my_config->INT_VAL_MUT_RATE() >= 0) {
int_rate = my_config->INT_VAL_MUT_RATE();
} else {
int_rate = local_rate;
}
if (random->GetDouble(0.0, 1.0) <= int_rate) {
interaction_val += random->GetRandNormal(0.0, local_size);
if(interaction_val < -1) interaction_val = -1;
else if (interaction_val > 1) interaction_val = 1;
//also modify infection chance, which is between 0 and 1
if(my_config->FREE_LIVING_SYMS()){
infection_chance += random->GetRandNormal(0.0, local_size);
if (infection_chance < 0) infection_chance = 0;
else if (infection_chance > 1) infection_chance = 1;
}
}
if (random->GetDouble(0.0, 1.0) <= eff_mut_rate) {
efficiency += random->GetRandNormal(0.0, local_size);
if(efficiency < 0) efficiency = 0;
else if (efficiency > 1) efficiency = 1;
}
}
#pragma clang diagnostic pop
emp::Ptr<Organism> MakeNew(){
emp::Ptr<EfficientSymbiont> sym_baby = emp::NewPtr<EfficientSymbiont>(random, my_world, my_config, GetIntVal());
sym_baby->SetInfectionChance(GetInfectionChance());
sym_baby->SetEfficiency(GetEfficiency());
return sym_baby;
}
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Woverloaded-virtual"
emp::Ptr<Organism> Reproduce(std::string mode) {
emp::Ptr<Organism> sym_baby = MakeNew();
sym_baby->Mutate(mode);
return sym_baby;
}
#pragma clang diagnostic pop
void VerticalTransmission(emp::Ptr<Organism> host_baby) {
if((my_world->WillTransmit()) && GetPoints() >= my_config->SYM_VERT_TRANS_RES()){ //if the world permits vertical tranmission and the sym has enough resources, transmit!
emp::Ptr<Organism> sym_baby = Reproduce("vertical");
host_baby->AddSymbiont(sym_baby);
//vertical transmission data node
emp::DataMonitor<int>& data_node_attempts_verttrans = my_world->GetVerticalTransmissionAttemptCount();
data_node_attempts_verttrans.AddDatum(1);
}
}
void HorizontalTransmission(emp::WorldPosition location) {
if (my_config->HORIZ_TRANS()) { //non-lytic horizontal transmission enabled
if(GetPoints() >= my_config->SYM_HORIZ_TRANS_RES()) {
// symbiont reproduces independently (horizontal transmission) if it has enough resources
// new symbiont in this host with mutated value
SetPoints(0); //TODO: test just subtracting points instead of setting to 0
emp::Ptr<Organism> sym_baby = Reproduce("horizontal");
emp::WorldPosition new_pos = my_world->SymDoBirth(sym_baby, location);
//horizontal transmission data nodes
emp::DataMonitor<int>& data_node_attempts_horiztrans = my_world->GetHorizontalTransmissionAttemptCount();
data_node_attempts_horiztrans.AddDatum(1);
emp::DataMonitor<int>& data_node_successes_horiztrans = my_world->GetHorizontalTransmissionSuccessCount();
if(new_pos.IsValid()){
data_node_successes_horiztrans.AddDatum(1);
}
}
}
}
};
#endif