|
bpp-phyl
2.1.0
|
00001 // 00002 // File: gBGC.cpp 00003 // Created by: Laurent Gueguen 00004 // Created on: lundi 13 février 2012, à 09h 42 00005 // 00006 00007 /* 00008 Copyright or © or Copr. CNRS, (November 16, 2004) 00009 This software is a computer program whose purpose is to provide 00010 classes for phylogenetic data analysis. 00011 00012 This software is governed by the CeCILL license under French law and 00013 abiding by the rules of distribution of free software. You can use, 00014 modify and/ or redistribute the software under the terms of the CeCILL 00015 license as circulated by CEA, CNRS and INRIA at the following URL 00016 "http://www.cecill.info". 00017 00018 As a counterpart to the access to the source code and rights to copy, 00019 modify and redistribute granted by the license, users are provided 00020 only with a limited warranty and the software's author, the holder of 00021 the economic rights, and the successive licensors have only limited 00022 liability. 00023 00024 In this respect, the user's attention is drawn to the risks associated 00025 with loading, using, modifying and/or developing or reproducing the 00026 software by the user in light of its specific status of free software, 00027 that may mean that it is complicated to manipulate, and that also 00028 therefore means that it is reserved for developers and experienced 00029 professionals having in-depth computer knowledge. Users are therefore 00030 encouraged to load and test the software's suitability as regards 00031 their requirements in conditions enabling the security of their 00032 systems and/or data to be ensured and, more generally, to use and 00033 operate it in the same conditions as regards security. 00034 00035 The fact that you are presently reading this means that you have had 00036 knowledge of the CeCILL license and that you accept its terms. 00037 */ 00038 00039 #include "gBGC.h" 00040 00041 // From the STL: 00042 #include <cmath> 00043 00044 using namespace bpp; 00045 00046 #include <Bpp/Numeric/Matrix/MatrixTools.h> 00047 #include <Bpp/Numeric/VectorTools.h> 00048 #include <Bpp/Numeric/Matrix/EigenValue.h> 00049 00050 /******************************************************************************/ 00051 00052 gBGC::gBGC(const NucleicAlphabet* alph, NucleotideSubstitutionModel* const pm, double gamma) : 00053 AbstractParameterAliasable("gBGC."), 00054 AbstractSubstitutionModel(alph,"gBGC."), 00055 pmodel_(pm->clone()), 00056 nestedPrefix_(pm->getNamespace()), 00057 gamma_(gamma) 00058 { 00059 pmodel_->setNamespace("gBGC."+nestedPrefix_); 00060 pmodel_->enableEigenDecomposition(0); 00061 addParameters_(pmodel_->getParameters()); 00062 addParameter_(new Parameter("gBGC.gamma", gamma_,new IntervalConstraint(-999, 10, true, true), true)); 00063 00064 updateMatrices(); 00065 } 00066 00067 gBGC::gBGC(const gBGC& gbgc) : 00068 AbstractParameterAliasable(gbgc), 00069 AbstractSubstitutionModel(gbgc), 00070 pmodel_(gbgc.pmodel_->clone()), 00071 nestedPrefix_(gbgc.nestedPrefix_), 00072 gamma_(gbgc.gamma_) 00073 { 00074 } 00075 00076 gBGC& gBGC::operator=(const gBGC& gbgc) 00077 { 00078 AbstractParameterAliasable::operator=(gbgc); 00079 AbstractSubstitutionModel::operator=(gbgc); 00080 pmodel_ = gbgc.pmodel_->clone(); 00081 nestedPrefix_ = gbgc.nestedPrefix_; 00082 gamma_=gbgc.gamma_; 00083 return *this; 00084 } 00085 00086 void gBGC::fireParameterChanged(const ParameterList& parameters) 00087 { 00088 pmodel_->matchParametersValues(parameters); 00089 AbstractSubstitutionModel::matchParametersValues(parameters); 00090 updateMatrices(); 00091 } 00092 00093 void gBGC::updateMatrices() 00094 { 00095 gamma_=getParameterValue("gamma"); 00096 unsigned int i,j; 00097 // Generator: 00098 double eg=exp(gamma_); 00099 for ( i = 0; i < 4; i++) 00100 for ( j = 0; j < 4; j++) 00101 generator_(i,j)=pmodel_->Qij(i,j); 00102 00103 generator_(0,1) *= eg; 00104 generator_(0,2) *= eg; 00105 generator_(3,1) *= eg; 00106 generator_(3,2) *= eg; 00107 00108 generator_(0,0) -= (generator_(0,1)+generator_(0,2))*(1-1/eg); 00109 generator_(3,3) -= (generator_(3,1)+generator_(3,2))*(1-1/eg); 00110 00111 // calcul spectral 00112 00113 EigenValue<double> ev(generator_); 00114 eigenValues_ = ev.getRealEigenValues(); 00115 00116 rightEigenVectors_ = ev.getV(); 00117 MatrixTools::inv(rightEigenVectors_,leftEigenVectors_); 00118 00119 iEigenValues_ = ev.getImagEigenValues(); 00120 00121 // frequence stationnaire 00122 double x = 0; 00123 j = 0; 00124 while (j < 4){ 00125 if (abs(eigenValues_[j]) < 0.000001 && abs(iEigenValues_[j]) < 0.000001) { 00126 eigenValues_[j]=0; //to avoid approximation problems in the future 00127 iEigenValues_[j]=0; //to avoid approximation problems in the future 00128 for (i = 0; i < 4; i++) 00129 { 00130 freq_[i] = leftEigenVectors_(j,i); 00131 x += freq_[i]; 00132 } 00133 break; 00134 } 00135 j++; 00136 } 00137 00138 for (i = 0; i < 4; i++) 00139 freq_[i] /= x; 00140 00141 // mise a l'echelle 00142 00143 x = 0; 00144 for (i = 0; i < 4; i++) 00145 x += freq_[i] * generator_(i,i); 00146 00147 MatrixTools::scale(generator_,-1 / x); 00148 00149 for (i = 0; i < 4; i++) 00150 eigenValues_[i] /= -x; 00151 00152 isDiagonalizable_=true; 00153 for (i = 0; i < size_ && isDiagonalizable_; i++) 00154 if (abs(iEigenValues_[i])> NumConstants::SMALL()){ 00155 isDiagonalizable_=false; 00156 break; 00157 } 00158 00159 // and the exchangeability_ 00160 for ( i = 0; i < size_; i++) 00161 for ( j = 0; j < size_; j++) 00162 exchangeability_(i,j) = generator_(i,j) / freq_[j]; 00163 00164 } 00165 00166 void gBGC::setNamespace(const std::string& prefix) 00167 { 00168 AbstractSubstitutionModel::setNamespace(prefix); 00169 // We also need to update the namespace of the nested model: 00170 pmodel_->setNamespace(prefix + nestedPrefix_); 00171 } 00172 00173 00174 std::string gBGC::getName() const 00175 { 00176 return "gBGC(model=" + pmodel_->getName()+")"; 00177 } 00178