|
bpp-phyl
2.1.0
|
00001 // 00002 // File: WordSubstitutionModel.cpp 00003 // Created by: Laurent Gueguen 00004 // Created on: Jan 2009 00005 // 00006 00007 /* 00008 Copyright or © or Copr. Bio++ Development Team, (November 16, 2004) 00009 This software is a computer program whose purpose is to provide classes 00010 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 only 00020 with a limited warranty and the software's author, the holder of the 00021 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 their 00031 requirements in conditions enabling the security of their systems and/or 00032 data to be ensured and, more generally, to use and operate it in the 00033 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 "WordSubstitutionModel.h" 00040 #include "FrequenciesSet/WordFrequenciesSet.h" 00041 00042 #include <Bpp/Numeric/Matrix/MatrixTools.h> 00043 #include <Bpp/Numeric/VectorTools.h> 00044 #include <Bpp/Numeric/Matrix/EigenValue.h> 00045 00046 // From SeqLib: 00047 #include <Bpp/Seq/Alphabet/WordAlphabet.h> 00048 #include <Bpp/Seq/Container/SequenceContainerTools.h> 00049 00050 using namespace bpp; 00051 00052 // From the STL: 00053 #include <cmath> 00054 00055 using namespace std; 00056 00057 /******************************************************************************/ 00058 00059 WordSubstitutionModel::WordSubstitutionModel( 00060 const std::vector<SubstitutionModel*>& modelVector, 00061 const std::string& st) : 00062 AbstractParameterAliasable((st == "") ? "Word." : st), 00063 AbstractSubstitutionModel(AbstractWordSubstitutionModel::extractAlph(modelVector), 00064 (st == "") ? "Word." : st), 00065 AbstractWordSubstitutionModel(modelVector, 00066 (st == "") ? "Word." : st) 00067 { 00068 size_t i, nbmod = VSubMod_.size(); 00069 00070 // relative rates 00071 for (i = 0; i < nbmod - 1; i++) 00072 { 00073 addParameter_(new Parameter("Word.relrate" + TextTools::toString(i + 1), 1.0 / static_cast<int>(nbmod - i), &Parameter::PROP_CONSTRAINT_EX)); 00074 } 00075 00076 WordSubstitutionModel::updateMatrices(); 00077 } 00078 00079 WordSubstitutionModel::WordSubstitutionModel( 00080 const Alphabet* alph, 00081 const std::string& st) : 00082 AbstractParameterAliasable((st == "") ? "Word." : st), 00083 AbstractSubstitutionModel(alph, 00084 (st == "") ? "Word." : st), 00085 AbstractWordSubstitutionModel(alph, 00086 (st == "") ? "Word." : st) 00087 {} 00088 00089 WordSubstitutionModel::WordSubstitutionModel( 00090 SubstitutionModel* pmodel, 00091 unsigned int num, 00092 const std::string& st) : 00093 AbstractParameterAliasable((st == "") ? "Word." : st), 00094 AbstractSubstitutionModel(pmodel->getAlphabet(), 00095 (st == "") ? "Word." : st), 00096 AbstractWordSubstitutionModel(pmodel, 00097 num, 00098 (st == "") ? "Word." : st) 00099 { 00100 size_t i; 00101 00102 // relative rates 00103 for (i = 0; i < num - 1; i++) 00104 { 00105 addParameter_(new Parameter("Word.relrate" + TextTools::toString(i + 1), 1.0 / static_cast<int>(num - i ), &Parameter::PROP_CONSTRAINT_EX)); 00106 } 00107 00108 WordSubstitutionModel::updateMatrices(); 00109 } 00110 00111 void WordSubstitutionModel::updateMatrices() 00112 { 00113 size_t i, nbmod = VSubMod_.size(); 00114 double x, y; 00115 x = 1.0; 00116 00117 for (i = 0; i < nbmod - 1; i++) 00118 { 00119 y = getParameterValue("relrate" + TextTools::toString(i + 1)); 00120 Vrate_[i] = x * y; 00121 x *= 1 - y; 00122 } 00123 Vrate_[nbmod - 1] = x; 00124 00125 AbstractWordSubstitutionModel::updateMatrices(); 00126 } 00127 00128 void WordSubstitutionModel::completeMatrices() 00129 { 00130 size_t nbmod = VSubMod_.size(); 00131 size_t i, p, j, m; 00132 size_t salph = getAlphabet()->getSize(); 00133 00134 // freq_ for this generator 00135 00136 for (i = 0; i < salph; i++) 00137 { 00138 freq_[i] = 1; 00139 j = i; 00140 for (p = nbmod - 1; p >= 0; p--) 00141 { 00142 m = VSubMod_[p]->getNumberOfStates(); 00143 freq_[i] *= VSubMod_[p]->getFrequencies()[j % m]; 00144 j /= m; 00145 } 00146 } 00147 } 00148 00149 const RowMatrix<double>& WordSubstitutionModel::getPij_t(double d) const 00150 { 00151 vector<const Matrix<double>*> vM; 00152 size_t nbmod = VSubMod_.size(); 00153 size_t i, j; 00154 00155 for (i = 0; i < nbmod; i++) 00156 { 00157 vM.push_back(&VSubMod_[i]->getPij_t(d * Vrate_[i] * rate_)); 00158 } 00159 00160 size_t t; 00161 double x; 00162 size_t i2, j2; 00163 size_t nbStates = getNumberOfStates(); 00164 size_t p; 00165 00166 for (i = 0; i < nbStates; i++) 00167 { 00168 for (j = 0; j < nbStates; j++) 00169 { 00170 x = 1.; 00171 i2 = i; 00172 j2 = j; 00173 for (p = nbmod; p > 0; p--) 00174 { 00175 t = VSubMod_[p - 1]->getNumberOfStates(); 00176 x *= (*vM[p - 1])(i2 % t, j2 % t); 00177 i2 /= t; 00178 j2 /= t; 00179 } 00180 pijt_(i, j) = x; 00181 } 00182 } 00183 return pijt_; 00184 } 00185 00186 const RowMatrix<double>& WordSubstitutionModel::getdPij_dt(double d) const 00187 { 00188 vector<const Matrix<double>*> vM, vdM; 00189 size_t nbmod = VSubMod_.size(); 00190 size_t i, j; 00191 00192 for (i = 0; i < nbmod; i++) 00193 { 00194 vM.push_back(&VSubMod_[i]->getPij_t(d * Vrate_[i] * rate_)); 00195 vdM.push_back(&VSubMod_[i]->getdPij_dt(d * Vrate_[i] * rate_)); 00196 } 00197 00198 size_t t; 00199 double x, r; 00200 size_t i2, j2; 00201 size_t nbStates = getNumberOfStates(); 00202 size_t p, q; 00203 00204 for (i = 0; i < nbStates; i++) 00205 { 00206 for (j = 0; j < nbStates; j++) 00207 { 00208 r = 0; 00209 for (q = 0; q < nbmod; q++) 00210 { 00211 i2 = i; 00212 j2 = j; 00213 x = 1; 00214 for (p = nbmod; p > 0; p--) 00215 { 00216 t = VSubMod_[p - 1]->getNumberOfStates(); 00217 if (q != p - 1) 00218 x *= (*vM[p - 1])(i2 % t, j2 % t); 00219 else 00220 x *= rate_ * Vrate_[p - 1] * (*vdM[p - 1])(i2 % t, j2 % t); 00221 i2 /= t; 00222 j2 /= t; 00223 } 00224 r += x; 00225 } 00226 dpijt_(i, j) = r; 00227 } 00228 } 00229 return dpijt_; 00230 } 00231 00232 const RowMatrix<double>& WordSubstitutionModel::getd2Pij_dt2(double d) const 00233 00234 { 00235 vector<const Matrix<double>*> vM, vdM, vd2M; 00236 size_t nbmod = VSubMod_.size(); 00237 size_t i, j; 00238 00239 for (i = 0; i < nbmod; i++) 00240 { 00241 vM.push_back(&VSubMod_[i]->getPij_t(d * Vrate_[i] * rate_)); 00242 vdM.push_back(&VSubMod_[i]->getdPij_dt(d * Vrate_[i] * rate_)); 00243 vd2M.push_back(&VSubMod_[i]->getd2Pij_dt2(d * Vrate_[i] * rate_)); 00244 } 00245 00246 00247 double r, x; 00248 size_t p, b, q, t; 00249 00250 size_t i2, j2; 00251 size_t nbStates = getNumberOfStates(); 00252 00253 00254 for (i = 0; i < nbStates; i++) 00255 { 00256 for (j = 0; j < nbStates; j++) 00257 { 00258 r = 0; 00259 for (q = 1; q < nbmod; q++) 00260 { 00261 for (b = 0; b < q; b++) 00262 { 00263 x = 1; 00264 i2 = i; 00265 j2 = j; 00266 for (p = nbmod; p > 0; p--) 00267 { 00268 t = VSubMod_[p - 1]->getNumberOfStates(); 00269 if ((p - 1 == q) || (p - 1 == b)) 00270 x *= rate_ * Vrate_[p - 1] * (*vdM[p - 1])(i2 % t, j2 % t); 00271 else 00272 x *= (*vM[p - 1])(i2 % t, j2 % t); 00273 00274 i2 /= t; 00275 j2 /= t; 00276 } 00277 r += x; 00278 } 00279 } 00280 00281 r *= 2; 00282 00283 for (q = 0; q < nbmod; q++) 00284 { 00285 x = 1; 00286 i2 = i; 00287 j2 = j; 00288 for (p = nbmod; p > 0; p--) 00289 { 00290 t = VSubMod_[p - 1]->getNumberOfStates(); 00291 if (q != p - 1) 00292 x *= (*vM[p - 1])(i2 % t, j2 % t); 00293 else 00294 x *= rate_ * rate_ * Vrate_[p - 1] * Vrate_[p - 1] * (*vd2M[p - 1])(i2 % t, j2 % t); 00295 00296 i2 /= t; 00297 j2 /= t; 00298 } 00299 r += x; 00300 } 00301 d2pijt_(i, j) = r; 00302 } 00303 } 00304 return d2pijt_; 00305 } 00306 00307 string WordSubstitutionModel::getName() const 00308 { 00309 size_t nbmod = VSubMod_.size(); 00310 string s = "WordSubstitutionModel model: " + VSubMod_[0]->getName(); 00311 for (size_t i = 1; i < nbmod - 1; i++) 00312 { 00313 s += " " + VSubMod_[i]->getName(); 00314 } 00315 00316 return s; 00317 } 00318 00319