bpp-phyl  2.1.0
Bpp/Phyl/Mapping/LaplaceSubstitutionCount.cpp
Go to the documentation of this file.
00001 //
00002 // File: LaplaceSubstitutionCount.cpp
00003 // Created by: Julien Dutheil
00004 // Created on: Wed Apr 5 11:21 2006
00005 //
00006 
00007 /*
00008    Copyright or © or Copr. Bio++ Development Team, (November 16, 2004, 2005, 2006)
00009 
00010    This software is a computer program whose purpose is to provide classes
00011    for phylogenetic data analysis.
00012 
00013    This software is governed by the CeCILL  license under French law and
00014    abiding by the rules of distribution of free software.  You can  use,
00015    modify and/ or redistribute the software under the terms of the CeCILL
00016    license as circulated by CEA, CNRS and INRIA at the following URL
00017    "http://www.cecill.info".
00018 
00019    As a counterpart to the access to the source code and  rights to copy,
00020    modify and redistribute granted by the license, users are provided only
00021    with a limited warranty  and the software's author,  the holder of the
00022    economic rights,  and the successive licensors  have only  limited
00023    liability.
00024 
00025    In this respect, the user's attention is drawn to the risks associated
00026    with loading,  using,  modifying and/or developing or reproducing the
00027    software by the user in light of its specific status of free software,
00028    that may mean  that it is complicated to manipulate,  and  that  also
00029    therefore means  that it is reserved for developers  and  experienced
00030    professionals having in-depth computer knowledge. Users are therefore
00031    encouraged to load and test the software's suitability as regards their
00032    requirements in conditions enabling the security of their systems and/or
00033    data to be ensured and,  more generally, to use and operate it in the
00034    same conditions as regards security.
00035 
00036    The fact that you are presently reading this means that you have had
00037    knowledge of the CeCILL license and that you accept its terms.
00038  */
00039 
00040 #include "LaplaceSubstitutionCount.h"
00041 
00042 #include <Bpp/Numeric/Matrix/MatrixTools.h>
00043 
00044 using namespace bpp;
00045 
00046 /******************************************************************************/
00047 
00048 void LaplaceSubstitutionCount::computeCounts(double length) const
00049 {
00050   RowMatrix<double> Q = model_->getGenerator();
00051   // L is the diagonal matrix with all substitution rates.
00052   size_t s = Q.getNumberOfRows();
00053   RowMatrix<double> QL(s, s);
00054   for (size_t i = 0; i < s; i++)
00055   {
00056     for (size_t j = 0; j < s; j++)
00057     {
00058       QL(i, j) = ((i == j) ? 0. : Q(i, j));
00059     }
00060   }
00061 
00062   MatrixTools::fill(m_, 0.);
00063   RowMatrix<double> M2(s, s);
00064   RowMatrix<double> M3(s, s);
00065   RowMatrix<double> M4(s, s);
00066   RowMatrix<double> M5(s, s);
00067   for (int n = 1; n < cutOff_; n++)
00068   {
00069     MatrixTools::fill(M2, 0.);
00070     for (int p = 0; p < n; p++)
00071     {
00072       MatrixTools::pow(Q, p, M3);         // Q^p -> M5
00073       MatrixTools::mult(M3, QL, M4);      // Q^p . QL -> M4
00074       MatrixTools::pow(Q, n - p - 1, M3); // Q^(n-p-1) -> M3
00075       MatrixTools::mult(M4, M3, M5);      // Q^p . QL . Q^(n-p-1) -> M5
00076       MatrixTools::add(M2, M5);
00077     }
00078     MatrixTools::scale(M2, pow(length, n) / NumTools::fact(n));
00079     MatrixTools::add(m_, M2);
00080   }
00081 
00082   // Now we must divide by pijt:
00083   RowMatrix<double> P = model_->getPij_t(length);
00084   for (size_t i = 0; i < s; i++)
00085   {
00086     for (size_t j = 0; j < s; j++)
00087     {
00088       m_(i, j) /= P(i, j);
00089     }
00090   }
00091 }
00092 
00093 /******************************************************************************/
00094 
00095 double LaplaceSubstitutionCount::getNumberOfSubstitutions(int initialState, int finalState, double length, size_t type) const
00096 {
00097   if (length == currentLength_)
00098     return m_(initialState, finalState);
00099   if (length < 0.000001)
00100     return initialState == finalState ? 0. : 1.;  // Limit case!
00101   // Else we need to recompute M:
00102   computeCounts(length);
00103 
00104   currentLength_ = length;
00105   return m_(initialState, finalState);
00106 }
00107 
00108 /******************************************************************************/
00109 
00110 Matrix<double>* LaplaceSubstitutionCount::getAllNumbersOfSubstitutions(double length, size_t type) const
00111 {
00112   if (length == currentLength_)
00113     return new RowMatrix<double>(m_);
00114   if (length < 0.000001) // Limit case!
00115   {
00116     size_t s = model_->getAlphabet()->getSize();
00117     for (size_t i = 0; i < s; i++)
00118     {
00119       for (size_t j = 0; j < s; j++)
00120       {
00121         m_(i, j) = i == j ? 0. : 1.;
00122       }
00123     }
00124   }
00125   else
00126   {
00127     // Else we need to recompute M:
00128     computeCounts(length);
00129   }
00130 
00131   currentLength_ = length;
00132 
00133   return new RowMatrix<double>(m_);
00134 }
00135 
00136 /******************************************************************************/
00137 
00138 void LaplaceSubstitutionCount::setSubstitutionModel(const SubstitutionModel* model)
00139 {
00140   model_ = model;
00141   size_t n = model->getAlphabet()->getSize();
00142   m_.resize(n, n);
00143   // Recompute counts:
00144   computeCounts(currentLength_);
00145 }
00146 
00147 /******************************************************************************/
00148 
 All Classes Namespaces Files Functions Variables Typedefs Friends