ILSPlainGradient.cpp 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. /**
  2. * @file ILSPlainGradient.cpp
  3. * @brief abstract interface for iterative linear solvers working with GenericMatrix
  4. * @author Erik Rodner
  5. * @date 12/21/2011
  6. */
  7. #include <iostream>
  8. #include "core/optimization/gradientBased/FirstOrderRasmussen.h"
  9. #include "core/optimization/gradientBased/FirstOrderTrustRegion.h"
  10. #include "ILSPlainGradient.h"
  11. using namespace NICE;
  12. using namespace std;
  13. ILSPlainGradient::ILSPlainGradient(bool verbose, int maxIterations, bool minResidual)
  14. {
  15. this->verbose = verbose;
  16. optimizer = new FirstOrderRasmussen(this->verbose);
  17. ( dynamic_cast< FirstOrderRasmussen * > (optimizer) )->setMaxIterations(maxIterations);
  18. // another optimization method
  19. //optimizer = new FirstOrderTrustRegion(0.1, false);
  20. //( dynamic_cast< FirstOrderTrustRegion * > (optimizer) )->setMaxIterations(maxIterations);
  21. this->minResidual = minResidual;
  22. }
  23. ILSPlainGradient::~ILSPlainGradient()
  24. {
  25. delete optimizer;
  26. }
  27. int ILSPlainGradient::solveLin ( const GenericMatrix & gm, const Vector & b, Vector & x )
  28. {
  29. if ( b.size() != gm.rows() ) {
  30. fthrow(Exception, "Size of vector b mismatches with the size of the given GenericMatrix.");
  31. }
  32. if ( x.size() != gm.cols() )
  33. {
  34. x.resize(gm.cols());
  35. x.set(0.0); // bad initial solution, but whatever
  36. }
  37. // use x as an initial solution
  38. ILSPlainGradientOptimizationProblem op ( &gm, b, x, this->minResidual );
  39. optimizer->optimizeFirst(op);
  40. x = op.position();
  41. return 0;
  42. }
  43. ILSPlainGradientOptimizationProblem::ILSPlainGradientOptimizationProblem( const GenericMatrix *gm, const Vector & b, const Vector & x0, bool minResidual ) : OptimizationProblemFirst(gm->cols())
  44. {
  45. this->m_gm = gm;
  46. this->m_b = b;
  47. this->parameters() = x0;
  48. this->minResidual = minResidual;
  49. }
  50. double ILSPlainGradientOptimizationProblem::computeObjective()
  51. {
  52. // we need to compute A*x
  53. Vector v_Ax;
  54. m_gm->multiply ( v_Ax, position() );
  55. if ( minResidual )
  56. {
  57. // we need to compute A*x-b
  58. Vector diff ( v_Ax - m_b );
  59. // ... and the quadratic norm
  60. return 0.5 * diff.scalarProduct(diff);
  61. } else {
  62. // x^T A x - b^T x = (A x - b)^T x (A is symmetric!)
  63. return (0.5 * v_Ax - m_b).scalarProduct ( position() );
  64. }
  65. }
  66. void ILSPlainGradientOptimizationProblem::computeGradient(Vector& newGradient)
  67. {
  68. // the gradient is A*(A*x - b) (note that we exploited the symmetry of A)
  69. Vector v_Ax;
  70. // we need to compute A*x
  71. m_gm->multiply ( v_Ax, position() );
  72. // we need to compute A*x-b
  73. Vector diff ( v_Ax - m_b );
  74. newGradient.resize ( m_gm->cols() );
  75. if ( minResidual )
  76. {
  77. // computing A*(Ax - b)
  78. m_gm->multiply ( newGradient, diff );
  79. } else {
  80. newGradient = diff;
  81. }
  82. }