/*+ ARES/HADES/BORG Package -- ./libLSS/tests/test_cg.cpp Copyright (C) 2014-2020 Guilhem Lavaux Copyright (C) 2009-2020 Jens Jasche Additional contributions from: Guilhem Lavaux (2023) +*/ #include #include "libLSS/tools/static_init.hpp" #include "libLSS/tools/optimization/cg.hpp" #include #include #include #include #include #include #include "libLSS/tools/optimization/array_helper.hpp" using namespace LibLSS; using boost::extents; using namespace CosmoTool; using namespace std; typedef Optimization::BoostArrayAllocator allocator_t; typedef allocator_t::array_t Array; void A(Array &out, Array const &in) { int N = in.shape()[0]; //initialize values for (int i = 0; i < N; i++) { out[i] = 0; for (int j = 0; j < N; j++) { //test with simple correlation function double Mij = 0.5 * exp(-0.5 * (i - j) * (i - j)); out[i] += Mij * in[j]; } } } int main(int argc, char **argv) { setupMPI(argc, argv); LibLSS::Console &console = LibLSS::Console::instance(); LibLSS::StaticInit::execute(); allocator_t allocator; CG cg(allocator); int N = 2000; boost::multi_array b(boost::extents[N]); boost::multi_array x0(boost::extents[N]); boost::multi_array x(boost::extents[N]); fwrap(b) = 1; fwrap(x) = 0; for (int i = 0; i < b.size(); i++) x0[i] = i; A(b, x0); cg.run(A, b, x); double max = 0; int imax = 0; double eps = 0.; for (int i = 0; i < b.size(); i++) { double diff = fabs(x[i] - x0[i]); if (max < diff) max = diff; imax = i; eps += diff * diff; } if (eps < 1e-5) std::cout << std::endl << "CG matrix inversion test passed!" << std::endl; else std::cout << "CG matrix inversion test failed!" << std::endl << std::endl; std::cout << "Distance between truth and solution = " << eps << std::endl; std::cout << "Largest deviation = " << max << " at element imax =" << imax << std::endl; LibLSS::StaticInit::finalize(); doneMPI(); return 0; }