FG.cpp 22.84 KiB
/*================================================*/
/*            Plants Functionals Groups           */
/*                 Definition Class               */
/*================================================*/
#include <cmath>
#include <iostream>
#include <cstring>
#include <fstream>
#include <cstdio>
#include "FG.h"
#include "FGUtils.h"
#include "Params.h"
using namespace std;
  /* Note : New version of FG constructor using Matt T. parameters handler utilities (Params.h) */
/*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
/* Constructors                                                                                    */
/*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
FG::FG() : m_Name(""), m_M(0), m_L(1), m_MaxA(ANone), m_ImmSize(0.0), m_StrataMax(0), m_Strata(0,1000), /* Life history*/
m_PoolL(PTcount,0), m_InnateDorm(false), m_PotentialFecundity(100), /* Propagule biology */
m_ActiveGerm(Rcount, PC100), m_Tolerance(LScount, vector<bool>(Rcount, true)), /* Light response */
m_Dispersed(false), m_disp50(0.0), m_disp99(0.0), m_dispLD(0.0), /* Dispersal module */
m_SoilContrib(0.0), m_SoilLow(0.0), m_SoilHigh(0.0), /* Soil response */
 m_SoilActiveGerm(Rcount, PC100), m_SoilTolerance(LScount, vector<Fract>(Rcount, PC100)), /* Soil response */
m_DistResponse(FGresponse()), /* Disturbance response */
m_FireResponse(FGresponse()), m_Flamm(0.0), /* Fire response */
m_DroughtResponse(FGresponse()), m_DroughtSD(2,0.0), m_CountModToSev(0), m_CountSevMort(0), m_DroughtRecovery(0), /* Drought response */
m_IsAlien(false) /* Alien module */
  	/* Nothing to do */
/*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/
void FG::getSuccParams(const GSP& glob_params, const string& PFG_LifeHistoryFile)
	/* 1. check parameter file existence */
	testFileExist("--PFG_LIFE_HISTORY_PARAMS--", PFG_LifeHistoryFile, false);
	/* 2. read succession parameters */
	par::Params SuccParams(PFG_LifeHistoryFile.c_str(), " = \"", "#"); /* opening PFG life history traits parameters file */
	cout << endl;
	cout << "*********************************************" << endl;
	cout << "** PFG : " << SuccParams.get_val<string>("NAME")[0] << endl;
	cout << "*********************************************" << endl;
	cout << endl;
	cout << "> Succession files opened" << endl;
	/* 3. fill FG object according to given parameters */
	/* PFG Life History parameters filling =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */
	m_Name = SuccParams.get_val<string>("NAME")[0];
	m_M = SuccParams.get_val<int>("MATURITY")[0];
	m_L = SuccParams.get_val<int>("LONGEVITY")[0];
	if (m_M >= m_L)
		cerr << "!!! MATURITY is superior or equal to LONGEVITY. Please check!" << endl;
		terminate();
	m_MaxA = Abund(SuccParams.get_val<int>("MAX_ABUNDANCE")[0]);
	m_ImmSize = FractToDouble(Fract(SuccParams.get_val<int>("IMM_SIZE")[0]));
	//m_StrataMax = SuccParams.get_val<int>("STRATA")[0];
7172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
vector<int> v_int = SuccParams.get_val<int>("STRATA", true); if (v_int.size()) m_StrataMax = v_int[0]; else m_StrataMax = glob_params.getNbStrata(); m_Strata = SuccParams.get_val<int>("CHANG_STR_AGES"); m_Strata.push_back(10000); /* High value of to avoid PFGs to exit the upper stata */ if (m_Strata.size() != glob_params.getNbStrata() + 1) { cerr << "!!! Wrong number of parameters provided for CHANG_STR_AGES (" << m_Strata.size() - 1; cerr << " instead of " << glob_params.getNbStrata() << "). Please check!" << endl; terminate(); } bool is_sup = false; int prev_age = m_Strata[0]; for(unsigned i=1; i<m_Strata.size(); i++) { if (m_Strata[i] < prev_age) { is_sup = true; } prev_age = m_Strata[i]; if (is_sup) { cerr << "!!! CHANG_STR_AGES must be given in ascending order. Please check!" << endl; terminate(); } } v_int = SuccParams.get_val<int>("IS_ALIEN", true); if (v_int.size()) m_IsAlien = v_int[0]; else m_IsAlien = false; /* Propagule biology parameters filling =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */ m_PoolL = SuccParams.get_val<int>("SEED_POOL_LIFE"); if (m_PoolL.size() != PTcount) { cerr << "!!! Wrong number of parameters provided for SEED_POOL_LIFE (" << m_PoolL.size() << " instead of " << PTcount << "). Please check!" << endl; terminate(); } m_InnateDorm = bool(SuccParams.get_val<int>("SEED_DORMANCY")[0]); /* Potential fecundity parameter filling =-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=- */ v_int = SuccParams.get_val<int>("POTENTIAL_FECUNDITY", true); if (v_int.size()) m_PotentialFecundity = v_int[0]; else m_PotentialFecundity = 100.0; cout << "> Life History parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getLightParams(const GSP& glob_params, const string& PFG_LightFile) { /* 1. check parameter file existence */ testFileExist("--PFG_LIGHT_PARAMS--", PFG_LightFile, false); /* 2. read light parameters */ par::Params LightParams(PFG_LightFile.c_str(), " = \"", "#"); vector<int> v_int = LightParams.get_val<int>("ACTIVE_GERM"); m_ActiveGerm = convert_int_to_enum<Fract>("ACTIVE_GERM", v_int, "Fract", Fcount); if (m_ActiveGerm.size() != Rcount) { cerr << "!!! Wrong number of parameters provided for ACTIVE_GERM (LIGHT) (" << m_ActiveGerm.size() << " instead of " << Rcount << "). Please check!" << endl; terminate(); } /* get shade tolerance as vector and reshape it into matrix format */ v_int = LightParams.get_val<int>("SHADE_TOL"); if (v_int.size() < (LScount-1) * Rcount) { cerr << "!!! Wrong number of parameters provided for SHADE_TOL (" << v_int.size() << " instead of " << (LScount-1) * Rcount << "). Please check!" << endl; terminate(); }
141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210
int counter = 0; m_Tolerance.resize(int(LScount)); for (int ls=1; ls<int(LScount); ls++) { m_Tolerance[ls].resize(int(Rcount)); for (int r=0; r<int(Rcount); r++) { m_Tolerance[ls][r] = v_int[counter]; counter ++; } } /* Propagule Light tolerance is assumed to be the same as germinants */ m_Tolerance[0].resize(int(Rcount)); for (int r=0; r<int(Rcount); r++) { m_Tolerance[0][r] = m_Tolerance[1][r]; } cout << "> PFGS light parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getDispParams(const GSP& glob_params, const string& PFG_DispersalFile) { /* 1. check parameter file existence */ testFileExist("--PFG_DISPERSAL_PARAMS--", PFG_DispersalFile, false); /* 2. read dispersal parameters */ par::Params DispParams(PFG_DispersalFile.c_str(), " = \"", "#"); m_Dispersed = false; vector<double> v_double = DispParams.get_val<double>("DISPERS_DIST"); if (v_double.size() == 3) { m_disp50 = v_double[0]; m_disp99 = v_double[1]; m_dispLD = v_double[2]; } else { cerr << "!!! Wrong number of parameters provided for DISPERS_DIST (" << v_double.size() << " instead of " << 3 << "). Please check!" << endl; terminate(); } if (m_disp99 < m_disp50 || m_dispLD < m_disp50 || m_dispLD < m_disp99) { cerr << "!!! DISPERS_DIST must be given in ascending order (disp50 <= disp99 <= dispLD). Please check!" << endl; terminate(); } cout << "> PFGS dispersal parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getDistParams(const GSP& glob_params, const string& PFG_DisturbancesFile) { m_DistResponse = FGresponse(PFG_DisturbancesFile, glob_params.getNbDisturbances(), glob_params.getNbDistSub()); cout << "> PFGS disturbances parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getSoilParams(const GSP& glob_params, const string& PFG_SoilFile) { /* 1. check parameter file existence */ testFileExist("--PFG_SOIL_PARAMS--", PFG_SoilFile, false); /* 2. read dispersal parameters */ par::Params SoilParams(PFG_SoilFile.c_str(), " = \"", "#");
211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280
m_SoilContrib = SoilParams.get_val<double>("SOIL_CONTRIB")[0]; m_SoilLow = SoilParams.get_val<double>("SOIL_LOW")[0]; m_SoilHigh = SoilParams.get_val<double>("SOIL_HIGH")[0]; if (m_SoilHigh < m_SoilContrib || m_SoilContrib < m_SoilLow || m_SoilHigh < m_SoilLow) { cerr << "!!! Soil values must be given in ascending order (SOIL_LOW <= SOIL_CONTRIB <= SOIL_HIGH). Please check!" << endl; terminate(); } vector<int> v_int = SoilParams.get_val<int>("ACTIVE_GERM"); m_SoilActiveGerm = convert_int_to_enum<Fract>("ACTIVE_GERM", v_int, "Fract", Fcount); if (m_SoilActiveGerm.size() != Rcount) { cerr << "!!! Wrong number of parameters provided for ACTIVE_GERM (SOIL) (" << m_SoilActiveGerm.size() << " instead of " << Rcount << "). Please check!" << endl; terminate(); } /* get soil tolerance as vector and reshape it into matrix format */ v_int = SoilParams.get_val<int>("SOIL_TOL", true); if (v_int.size() != Rcount * (LScount - 1)) { cerr << "!!! Wrong number of parameters provided for SOIL_TOL (" << v_int.size() << " instead of " << Rcount * (LScount - 1) << "). Please check!" << endl; terminate(); } int counter = 0; m_SoilTolerance.resize(int(LScount)); for (unsigned i=1; i<m_SoilTolerance.size(); i++) { // fill automatically germinant LS case ==> not use at time m_SoilTolerance[i].resize(Rcount); for (unsigned j=0; j<m_SoilTolerance[i].size(); j++) { m_SoilTolerance[i][j] = convert_int_to_enum<Fract>("SOIL_TOL", v_int[counter], "Fract", Fcount); counter ++; } } /* Propagule Soil tolerance is assumed to be the same as germinants */ m_SoilTolerance[0].resize(Rcount); for (unsigned c=0; c<m_SoilTolerance[0].size(); c++) { m_SoilTolerance[0][c] = m_SoilTolerance[1][c]; } cout << "> PFGS soil parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getFireParams(const GSP& glob_params, const string& PFG_FiresFile) { /* 1. check parameter file existence */ testFileExist("--PFG_FIRES_PARAMS--", PFG_FiresFile, false); /* 2. read fire disturbance parameters */ par::Params FireParams(PFG_FiresFile.c_str(), " = \"", "#"); m_FireResponse = FGresponse(PFG_FiresFile, glob_params.getNbFireDisturbances(), glob_params.getNbFireSub()); m_Flamm = FireParams.get_val<double>("FLAMMABILITY")[0]; cout << "> PFGS fires parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ void FG::getDrouParams(const GSP& glob_params, const string& PFG_DroughtFile) { /* 1. check parameter file existence */ testFileExist("--PFG_DROUGHT_PARAMS--", PFG_DroughtFile, false); /* 2. read drought disturbance parameters */ par::Params DroughtParams(PFG_DroughtFile.c_str(), " = \"", "#"); m_DroughtResponse = FGresponse(PFG_DroughtFile, 2, glob_params.getNbDroughtSub());
281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350
m_DroughtSD = DroughtParams.get_val<double>("DROUGHT_SD"); m_CountModToSev = DroughtParams.get_val<unsigned>("COUNT_MOD_TO_SEV")[0]; m_CountSevMort = DroughtParams.get_val<unsigned>("COUNT_SEV_MORT")[0]; m_DroughtRecovery = DroughtParams.get_val<unsigned>("DROUGHT_RECOVERY")[0]; cout << "> PFGS drought parameters provided" << endl; } /*-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-*/ FG::FG(const GSP& glob_params, const FOPL& file_of_params, const unsigned& fg_id) { bool wrong_identifier = false; bool doLight = glob_params.getDoLightCompetition(); bool doDisp = glob_params.getDoDispersal(); bool doDist = glob_params.getDoDisturbances(); bool doSoil = glob_params.getDoSoilCompetition(); bool doFire = glob_params.getDoFireDisturbances(); bool doDrought = glob_params.getDoDroughtDisturbances(); if (fg_id < file_of_params.getFGLifeHistory().size()) { getSuccParams(glob_params,file_of_params.getFGLifeHistory()[fg_id]); if (doLight) { if (fg_id < file_of_params.getFGLight().size()) { getLightParams(glob_params,file_of_params.getFGLight()[fg_id]); } else { wrong_identifier = true; } } else { m_ActiveGerm.resize(int(Rcount), PC100); m_Tolerance.resize(int(LScount), vector<bool>(Rcount, true)); } if (doDisp) { if (fg_id < file_of_params.getFGDispersal().size()) { getDispParams(glob_params,file_of_params.getFGDispersal()[fg_id]); } else { wrong_identifier = true; } } else { m_Dispersed = false; m_disp50 = 0.0; m_disp99 = 0.0; m_dispLD = 0.0; } if (doSoil) { if (fg_id < file_of_params.getFGSoil().size()) { getSoilParams(glob_params,file_of_params.getFGSoil()[fg_id]); } else { wrong_identifier = true; } } else { m_SoilContrib = 0.0; m_SoilLow = 0.0; m_SoilHigh = 0.0; m_SoilActiveGerm.resize(int(Rcount), PC100); m_SoilTolerance.resize(int(LScount), vector<Fract>(Rcount, PC100)); //m_SoilTolerance.resize(int(LScount), vector<bool>(1, true));