ReturnMatrix Cholesky(const SymmetricBandMatrix& S)
{
   REPORT
   Tracer trace("Band-Cholesky");
   int nr = S.Nrows(); int m = S.lower_val;
   LowerBandMatrix T(nr,m);
   Real* s = S.Store(); Real* t = T.Store(); Real* ti = t;

   for (int i=0; i<nr; i++)
   {
      Real* tj = t; Real sum; int l;
      if (i<m) { REPORT l = m-i; s += l; ti += l; l = i; }
      else { REPORT t += (m+1); l = m; }

      for (int j=0; j<l; j++)
      {
         Real* tk = ti; sum = 0.0; int k = j; tj += (m-j);
         while (k--) { sum += *tj++ * *tk++; }
         *tk = (*s++ - sum) / *tj++;
      }
      sum = 0.0;
      while (l--) { sum += square(*ti++); }
      Real d = *s++ - sum;
      if (d<=0.0)  Throw(NPDException(S));
      *ti++ = sqrt(d);
   }

   T.release(); return T.for_return();
}
예제 #2
0
 void CholeskySolver<TYPE>::Solve(const BaseMatrix<TYPE> &in, BaseMatrix<TYPE> &out) const
 {
     assert(in.Nrows() == lm.Ncols());
     assert(in.Nrows() == out.Nrows() && in.Ncols() == out.Ncols());
     if (LinearEquationSolver<TYPE>::fail)
     {
         Singleton<Tracer>::Instance()->AddMessage("CholeskySolver::Solve(in, out)");
         throw NPDException(SimpleSolver<TYPE>::mat);
     }
     Matrix<TYPE> temp(out.Nrows(), out.Ncols());
     lm.Solve(in, temp);
     t(lm).Solve(temp, out);
 }
예제 #3
0
 LogAndSign<TYPE> CholeskySolver<TYPE>::LogDeterminant() const
 {
     if (LinearEquationSolver<TYPE>::fail)
     {
         Singleton<Tracer>::Instance()->AddMessage("CholeskySolver::LogDeterminant()");
         throw NPDException(SimpleSolver<TYPE>::mat);
     }
     LogAndSign<TYPE> ld;
     int n = lm.Nrows();
     for (int i = 1; i <= n; ++i)
     {
         ld *= lm(i, i);
     }
     ld.PowEq(2);
     return ld;
 }
ReturnMatrix Cholesky(const SymmetricMatrix& S)
{
   REPORT
   Tracer trace("Cholesky");
   int nr = S.Nrows();
   LowerTriangularMatrix T(nr);
   Real* s = S.Store(); Real* t = T.Store(); Real* ti = t;
   for (int i=0; i<nr; i++)
   {
      Real* tj = t; Real sum; int k;
      for (int j=0; j<i; j++)
      {
         Real* tk = ti; sum = 0.0; k = j;
         while (k--) { sum += *tj++ * *tk++; }
         *tk = (*s++ - sum) / *tj++;
      }
      sum = 0.0; k = i;
      while (k--) { sum += square(*ti++); }
      Real d = *s++ - sum;
      if (d<=0.0)  Throw(NPDException(S));
      *ti++ = sqrt(d);
   }
   T.release(); return T.for_return();
}