cghs.hh 1.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546
  1. // -*- mode: c++; coding: utf-8 -*-
  2. // ra-ra/examples - Conjugate gradient after Hestenes und Stiefel.
  3. // (c) Daniel Llorens - 2017
  4. // This library is free software; you can redistribute it and/or modify it under
  5. // the terms of the GNU Lesser General Public License as published by the Free
  6. // Software Foundation; either version 3 of the License, or (at your option) any
  7. // later version.
  8. // Adapted from lsolver/cghs.cc by Christian Badura, 1998/05.
  9. #pragma once
  10. #include "ra/ra.hh"
  11. template <class A, class B, class X, class W>
  12. inline int
  13. cghs(A & a, B const & b, X & x, W & work, double eps)
  14. {
  15. using ra::sqr;
  16. work = 0.;
  17. auto g = work(0);
  18. auto r = work(1);
  19. auto p = work(2);
  20. double err = sqr(eps)*reduce_sqrm(b);
  21. mult(a, x, g);
  22. g = b-g;
  23. r = g;
  24. int i;
  25. for (i=0; reduce_sqrm(g)>err; ++i) {
  26. mult(a, r, p);
  27. double rho = reduce_sqrm(p);
  28. double sig = dot(r, p);
  29. double tau = dot(g, r);
  30. double t = tau/sig;
  31. double gam = (sqr(t)*rho-tau)/tau;
  32. x += t*r;
  33. g -= t*p;
  34. r = r*gam + g;
  35. }
  36. return i;
  37. }